You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Jackson Databind 2.17+中@JsonAnySetter失效?如何恢复旧行为?

问题解答

是的,@JsonAnySetter的行为在Jackson 2.17版本确实发生了变更,核心原因是Jackson Kotlin模块对Kotlin数据类中只读属性(val)的处理逻辑变得更严格了。

在2.15.x版本中,即使otherContent是val修饰的Map属性,Jackson会默认将其视为可修改的容器,自动把未知字段填充进去。但2.17版本开始,Jackson严格遵循Kotlin的属性可变性规则:val标记的属性是只读的,无法直接通过Setter修改,因此不再自动将未知字段映射到这个Map中,导致最终otherContent为空。

修复方案(任选其一即可)

  • 方案1:将属性改为可变类型(var)
    把otherContent的val改成var,同时明确使用可变Map类型,让Jackson可以直接修改这个容器:

    @JsonIgnoreProperties(ignoreUnknown = true)
    data class MyDTO(val type: String, @JsonAnySetter var otherContent: MutableMap<String, String> = HashMap())
    
  • 方案2:保留val,添加专门的@JsonAnySetter方法
    如果想保持属性只读,可以单独写一个方法来处理未知字段,手动填充到otherContent中:

    @JsonIgnoreProperties(ignoreUnknown = true)
    data class MyDTO(val type: String, val otherContent: MutableMap<String, String> = HashMap()) {
        @JsonAnySetter
        fun addToOtherContent(key: String, value: String) {
            otherContent[key] = value
        }
    }
    
  • 方案3:恢复旧版行为(不推荐)
    通过配置强制Jackson将只读属性当作Setter使用,不过这种方式可能在后续版本中被移除,兼容性较差:

    val objectMapper = jacksonObjectMapper().apply {
        configure(DeserializationFeature.USE_READ_ONLY_PROPERTY_AS_SETTER, true)
    }
    

内容的提问来源于stack exchange,提问作者Johan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.21 09:40:09