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

Jackson反序列化遇未知属性未报错问题求助

Jackson反序列化未触发未知属性异常排查

根据Jackson官方文档,FAIL_ON_UNKNOWN_PROPERTIES默认开启,当JSON包含额外字段时,MyFormLayout类的反序列化应抛出UnrecognizedPropertyException。但即使通过Spring配置显式设置该属性为true,测试仍未触发预期异常,需要排查原因。

相关代码与信息

POJO代码

@Getter
@Setter
@FieldNameConstants
@ToString
@Builder
@Document(collection = "form_layouts")
@EqualsAndHashCode(callSuper = true, onlyExplicitlyIncluded = true)
@Jacksonized
public class MyFormLayout extends AuditableDocument {

    @NotNull
    private Boolean selected;
    @NotNull
    private Boolean disabled;
    @NotEmpty
    private List<Layout> layout;

    @NotBlank
    @EqualsAndHashCode.Include
    private String realmId;
}

测试代码

@SpringJUnitConfig
@TestPropertySource(
        properties = {
                "spring.jackson.deserialization.fail-on-unknown-properties=true"
        }
)
@AutoConfigureJson
@DisplayName("Form Layout Deserialisation")
public class MyFormLayoutDeserialisationTest {

    @Autowired
    Jackson2ObjectMapperBuilder objectMapperBuilder;
    ObjectMapper objectMapper;

    @BeforeEach
    void setUp() {
        objectMapper = objectMapperBuilder.build();
    }

    @Test
    @DisplayName("fails loading seeder json if the keys don't match to object fields")
    void testForcesJsonToMatchFormTemplate(@Value("classpath:bad_nform_layout.json") Resource badLayout) {
        Assertions.assertThrows(UnrecognizedPropertyException.class, () -> objectMapper.readValue(Files.readString(Path.of(badLayout.getFile().getAbsolutePath())), new TypeReference<>() {
        }), "Seeder JSON should have the exact keys and fields declared in the MyFormLayout object");
    }
}

测试报错信息

org.opentest4j.AssertionFailedError: Seeder JSON should have the exact keys and fields declared in the MyFormLayout object ==> Expected com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException to be thrown, but nothing was thrown.

测试用JSON文件(含未知属性"foo":"bar")

[
  {
    "selected": false,
    "disabled": true,
    "app": "blox",
    "foo": "bar",
    "layout": [
      {
        "id": "B-1",
        "x": 0,
        "y": 0,
        "w": 12,
        "h": 7
      },
      {
        "id": "B-2",
        "x": 13,
        "y": 0,
        "w": 4,
        "h": 4
      },
      {
        "id": "B-3",
        "x": 0,
        "y": 8,
        "w": 12,
        "h": 3
      },
      {
        "id": "B-4",
        "x": 13,
        "y": 5,
        "w": 4,
        "h": 6
      }
    ]
  }
  ...
]

排查原因与解决方案

1. TypeReference未指定正确的目标类型

测试代码中使用new TypeReference<>() {}进行泛型推断,但JSON是数组结构,实际需要反序列化为List<MyFormLayout>。当前匿名的TypeReference会让Jackson将JSON数组反序列化为List<Object>,而Object类型可以接受任意属性,自然不会触发未知属性异常。

修复方式:明确指定TypeReference的目标类型:

new TypeReference<List<MyFormLayout>>() {}

2. 父类AuditableDocument可能存在忽略未知属性的配置

检查父类AuditableDocument是否添加了@JsonIgnoreProperties(ignoreUnknown = true)注解。如果父类配置了忽略未知属性,子类会继承该配置,导致即使子类开启了FAIL_ON_UNKNOWN_PROPERTIES也不会生效。

修复方式:如果父类有该注解,移除它;或者在子类显式覆盖配置:

@JsonIgnoreProperties(ignoreUnknown = false)
public class MyFormLayout extends AuditableDocument {
    // ... 原有代码
}

3. 确认Jackson配置是否真正生效

可以在测试中打印ObjectMapper的配置,验证FAIL_ON_UNKNOWN_PROPERTIES是否为true:

System.out.println(objectMapper.getDeserializationConfig().isEnabled(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES));

如果输出为false,说明Spring配置未正确生效,需要检查是否有其他配置类覆盖了该属性,或者直接在测试中手动设置:

objectMapper.enable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.08 22:47:26