我正在尝试将json反序列化为多态类的简单示例。反序列化失败,错误:
org.codehaus.jackson.map.JsonMappingException: Could not resolve type id 'aField' into a subtype of [simple type, class ...SubClassA]
如果我尝试对单个子类进行反序列化,只使用该类的JSON,它就会成功,但是当我将这两个类放在SubClassTestObject中时,它会失败。有什么想法解决这个问题?我是否需要编写自定义反序列化器?
这是我的JSON:
{
"classA":{
"aField":"A",
"baseField":"baseA"
},
"classB":{
"baseField":"baseB",
"bField":"B"
}
}
以下是我的课程:
@JsonTypeInfo(use=JsonTypeInfo.Id.NAME, include=JsonTypeInfo.As.WRAPPER_OBJECT)
@JsonSubTypes({
@JsonSubTypes.Type(value = SubClassA.class, name = "classA"),
@JsonSubTypes.Type(value = SubClassB.class, name = "classB")
})
@JsonIgnoreProperties(ignoreUnknown = true)
public abstract class AbstractSimpleClass {
String baseField;
public String getBaseField() {
return baseField;
}
public void setBaseField(String baseField) {
this.baseField = baseField;
}
}
public class SubClassA extends AbstractSimpleClass {
String aField;
public String getaField() {
return aField;
}
public void setaField(String aField) {
this.aField = aField;
}
}
public class SubClassB extends AbstractSimpleClass {
String bField;
public String getbField() {
return bField;
}
public void setbField(String bField) {
this.bField = bField;
}
}
@JsonIgnoreProperties(ignoreUnknown = true)
public class SubClassTestObject {
@JsonProperty("classA")
SubClassA a;
@JsonProperty("classB")
SubClassB b;
public SubClassA getA() {
return a;
}
public void setA(SubClassA a) {
this.a = a;
}
public SubClassB getB() {
return b;
}
public void setB(SubClassB b) {
this.b = b;
}
}
这是我的测试:
@Test
public void testBoth() throws IOException, URISyntaxException {
ClassLoader classLoader = getClass().getClassLoader();
json = new String(Files.readAllBytes(Paths.get(classLoader.getResource("test/so-example.json").toURI())));
ObjectMapper mapper = new ObjectMapper();
mapper.registerSubtypes(SubClassA.class, SubClassB.class);
SubClassTestObject testObj = mapper.readValue(json, SubClassTestObject.class); //Fails here
SubClassA a = testObj.getA();
SubClassB b = testObj.getB();
assertTrue(a.getBaseField().equals("baseA"));
assertTrue(b.getBaseField().equals("baseB"));
assertTrue(a.getaField().equals("A"));
assertTrue(b.getbField().equals("B"));
}
答案 0 :(得分:1)
编辑后:
此
@JsonProperty("classA")
SubClassA a;
与
完全无关@JsonTypeInfo(use=JsonTypeInfo.Id.NAME, include=JsonTypeInfo.As.WRAPPER_OBJECT)
JsonTypeInfo.As.WRAPPER_OBJECT
意味着隐含。这不是您在POJO中映射的内容。您将无法使用此策略映射当前的JSON。例如,执行以下操作或更改JsonTypeInfo
以使用JsonTypeInfo.As.PROPERTY
,然后在JSON中提供相应的@type
(及其相应的值)属性。
预编辑:
您的SubClassTestObject
课程有两个属性,a
和b
,因为
public SubClassA getA() {
return a;
}
public SubClassB getB() {
return b;
}
这些在您的JSON中不存在。既然你告诉杰克逊忽略了未知的属性,它就不会反序列化。但是,它们都将保持未初始化状态。
您要反序列化的JSON是
{
"a": {
"classA": {
"aField": "A",
"baseField": "baseA"
}
},
"b": {
"classB": {
"baseField": "baseB",
"bField": "B"
}
}
}
对您的根a
对象有b
和SubClassTestObject
。并且那些使用具有适当JsonTypeInfo
名称的包装器对象。