当我第一次尝试您的 SomeData 类并对其进行序列化时,我得到了以下结果:
{"tnAvailable":true,"sTempChange":"trial_000","stempChange":"trial_000"}
这意味着 jackson 不将您的 getter/setter 与 sTempChange 属性匹配,它们被视为不同的属性。为我的映射器添加以下配置后,我能够重现您的情况:
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.NONE);
objectMapper.setVisibility(PropertyAccessor.GETTER, JsonAutoDetect.Visibility.ANY);
objectMapper.setVisibility(PropertyAccessor.SETTER, JsonAutoDetect.Visibility.ANY);
objectMapper.setVisibility(PropertyAccessor.IS_GETTER, JsonAutoDetect.Visibility.ANY);
现在你的错误的原因是因为 Jackson 使用它自己的 bean 实用程序实现 (com.fasterxml.jackson.databind.util.BeanUtil),当一个实例被序列化时,当一个类处理字段、getter 和 setter 时使用它(由com.fasterxml.jackson.databind.introspect.POJOPropertiesCollector 完成) /反序列化。感兴趣的方法是okNameForGetter 和okNameForSetter。在这些方法中,根据MapperFeature.USE_STD_BEAN_NAMING 使用了另外两种方法(它在所有方法中的stdNaming 参数中传递)。这两种方法的使用方式如下:
return stdNaming
? stdManglePropertyName(name, prefix.length())
: legacyManglePropertyName(name, prefix.length());
stdManglePropertyName 遵循第 8.8 节中的 Java Beans 规范,而 legacyManglePropertyName 不遵循并且在 Jackson 2.5 之前的版本中使用。
现在,在通过这些方法运行 getter 和 setter 方法名称之后,但是您设置了 MapperFeature.USE_STD_BEAN_NAMING,sTempChange 属性的 getter/setter 名称错误。应该是getsTempChange(小写's')和getsTempChange(还是小写's')才能正确序列化和反序列化SomeData类的实例。
最后是一些测试代码:
import com.fasterxml.jackson.databind.ObjectMapper;
public class Test {
static class SomeData {
public boolean tnAvailable;
public String sTempChange;
public String getsTempChange() {
return sTempChange;
}
public void setsTempChange(String sTempChange) {
this.sTempChange = sTempChange;
}
public boolean isTnAvailable() {
return tnAvailable;
}
public void setTnAvailable(boolean tnAvailable) {
this.tnAvailable = tnAvailable;
}
}
public static void main(String[] args) {
ObjectMapper objectMapper = new ObjectMapper();
// objectMapper.configure(MapperFeature.USE_STD_BEAN_NAMING, true);
SomeData someData = new SomeData();
someData.setsTempChange("trial_000");
someData.setTnAvailable(true);
// objectMapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.NONE);
// objectMapper.setVisibility(PropertyAccessor.GETTER, JsonAutoDetect.Visibility.ANY);
// objectMapper.setVisibility(PropertyAccessor.SETTER, JsonAutoDetect.Visibility.ANY);
// objectMapper.setVisibility(PropertyAccessor.IS_GETTER, JsonAutoDetect.Visibility.ANY);
try {
System.out.println("Serialize: " + objectMapper.writeValueAsString(someData));
String json = "{ \"tnAvailable\": false, \"sTempChange\": \"trial_001\" }";
SomeData anotherData = objectMapper.readValue(json, SomeData.class);
System.out.println("Deserialize: " + anotherData.isTnAvailable() + ", " + anotherData.getsTempChange());
} catch (Exception e) {
e.printStackTrace();
}
}
}