Java JSON with Jackson:Desiralize在使用抽象方法时失败(多态类型处理)

Java JSON with Jackson:Desiralize在使用抽象方法时失败(多态类型处理),java,json,jackson,Java,Json,Jackson,我有一个关于Jackson的Json反序列化的问题(编辑:2.0.4版本)。我想将一个包含其他Bean列表的Bean序列化为string,保存这个字符串,然后在以后反序列化这个字符串。我使用一些基类及其子类型。基类父类是一个抽象类,它有两个带有getter和setter的属性,这个类还有一个抽象方法getType()。其他抽象类AbstractChild从类父级继承。此类也具有属性和isExportEnabled()抽象方法。 如果这个Bean被序列化,我没有问题。我在父类上使用以下注释 *@J

我有一个关于Jackson的Json反序列化的问题(编辑:2.0.4版本)。我想将一个包含其他Bean列表的Bean序列化为string,保存这个字符串,然后在以后反序列化这个字符串。我使用一些基类及其子类型。基类父类是一个抽象类,它有两个带有getter和setter的属性,这个类还有一个抽象方法getType()。其他抽象类AbstractChild从类父级继承。此类也具有属性和isExportEnabled()抽象方法。 如果这个Bean被序列化,我没有问题。我在父类上使用以下注释 *@JsonTypeInfo(use=JsonTypeInfo.Id.MINIMAL_类,include=JsonTypeInfo.As.PROPERTY,PROPERTY=“@cls”)* 将生成该字符串。 但是Desiralize失败:将引发异常“Unrecognized field”类型“”。但我需要这个属性!我试图在抽象方法上设置@JsonProperty(“type”),这没有效果。 请帮帮我

编辑:如果我引入私有字段“type”(父)和“exportEnabled”(AbstractChild),那么它将正确运行。 这是个例外

com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException: 无法识别的字段“type”(类tst.SimpleTestMain$FirstChild),不是 标记为可忽略(4个已知属性:,“id”,“maxCount”,“code”, “minCount”]),位于[源代码:java.io。StringReader@1ad9fa;行:1, 列:125](通过参考链: tst.Fam[“成员”]->tst.FirstChild[“类型”])位于 com.fasterxml.jackson.databind.exc.UnrecognizedPropertyException.from(UnrecognizedPropertyException.java:79) 在 com.fasterxml.jackson.databind.DeserializationContext.reportUnknownProperty(DeserializationContext.java:568)

…以及示例类
package-tst;
导入java.io.IOException;
导入java.util.ArrayList;
导入java.util.List;
导入com.fasterxml.jackson.annotation.JsonProperty;
导入com.fasterxml.jackson.annotation.JsonTypeInfo;
导入com.fasterxml.jackson.databind.ObjectMapper;
公共类SimpleTestMain{
枚举类型{
A型,B型
}
@JsonTypeInfo(use=JsonTypeInfo.Id.MINIMAL_类,include=JsonTypeInfo.As.PROPERTY,PROPERTY=“@cls”)
公共静态抽象类父类{
私有int-id;
私有字符串码;
公共家长(){
}
@JsonProperty(“类型”)
//第一抽象吸气剂
公共抽象类型getType();
公共int getId(){
返回id;
}
公共无效集合id(内部id){
this.id=id;
}
公共字符串getCode(){
返回码;
}
公共无效设置码(字符串码){
this.code=代码;
}
}
公共静态抽象类AbstractChild扩展父类{
私有整数minCount;
私有整数最大计数;
公共儿童(){
}
//第二种抽象方法:布尔使用
公共抽象布尔值isExportEnabled();
public int getMinCount(){
返回minCount;
}
公共void setMinCount(int minCount){
this.minCount=minCount;
}
public int getMaxCount(){
返回最大计数;
}
公共void setMaxCount(int maxCount){
this.maxCount=maxCount;
}
}
公共静态类FirstChild扩展了AbstractChild{
@凌驾
公共布尔值isExportEnabled(){
返回false;
}
@凌驾
公共类型getType(){
返回类型。类型_A;
}
}
公共静态类SecondChild扩展AbstractChild{
@凌驾
公共布尔值isExportEnabled(){
返回true;
}
@凌驾
公共类型getType(){
返回类型.Type_B;
}
}
公共静态类Fam{
私人家庭;
非公开名单成员;
公共金融资产管理公司(){
members=newarraylist();
}
public int getFamId(){
回归家园;
}
公共无效setFamId(int famId){
this.famId=famId;
}
公共列表getMembers(){
返回成员;
}
公共成员(列表成员){
这个.成员=成员;
}
公共无效添加成员(父成员){
成员。添加(成员);
}
}
公共SimpleTestMain(){
}
公共静态void main(字符串[]args){
Fam=new Fam();
FirstChild fc=新的FirstChild();
fc.setId(1);
fc.设置代码(“第一儿童代码”);
fc.setMinCount(1);
fc.setMaxCount(4);
家族成员(fc);
SecondChild sc=新的SecondChild();
sc.setCode(“第二儿童代码”);
sc.setMinCount(131);
sc.setMaxCount(431);
家族成员(资深大律师);
字符串测试=”;
//序列化它
ObjectMapper mapper=新的ObjectMapper();
试一试{
test=mapper.writeValueAsString(fam);
System.out.println(“序列化bean:\n”+测试);
//输出
//序列化bean:
//{“famId”:0,“members”:[{“@cls:”.SimpleTestMain$FirstChild”,“id”:1,“code”:“FirstChildCode”,“minCount”:1,“maxCount”:4,“type”:“type_A”,“exportEnabled”:false},{“@cls:”.SimpleTestMain$SecondChild”,“id”:0,“code”:“SecondChildCode”,“minCount”:131,“maxCount”:431,“type”:“type_B”,“exportEnabled”:true}
}捕获(IOE异常){
e、 printStackTrace();
}
//反序列化它
映射器=新的ObjectMapper();
//mapper.enableDefaultTyping();
试一试{
Fam fam1=mapper.readValue(test,Fam.class);
}捕获(IOE异常){
e、 printStackTrace();
}
}
}
如果您解决了y
package tst;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonTypeInfo;
import com.fasterxml.jackson.databind.ObjectMapper;

public class SimpleTestMain {

    enum Type {
        TYPE_A, TYPE_B
    }

    @JsonTypeInfo(use = JsonTypeInfo.Id.MINIMAL_CLASS, include = JsonTypeInfo.As.PROPERTY, property = "@cls")
    public static abstract class Parent {

        private int id;

        private String code;

        public Parent() {

        }
        @JsonProperty("type")
        // First abstract getter
        public abstract Type getType();

        public int getId() {
            return id;
        }

        public void setId(int id) {
            this.id = id;
        }

        public String getCode() {
            return code;
        }

        public void setCode(String code) {
            this.code = code;
        }

    }

    public static abstract class AbstractChild extends Parent {

        private int minCount;

        private int maxCount;

        public AbstractChild() {

        }

        // Second abstract method: boolean used
        public abstract boolean isExportEnabled();

        public int getMinCount() {
            return minCount;
        }

        public void setMinCount(int minCount) {
            this.minCount = minCount;
        }

        public int getMaxCount() {
            return maxCount;
        }

        public void setMaxCount(int maxCount) {
            this.maxCount = maxCount;
        }

    }

    public static class FirstChild extends AbstractChild {

        @Override
        public boolean isExportEnabled() {
            return false;
        }

        @Override
        public Type getType() {
            return Type.TYPE_A;
        }

    }

    public static class SecondChild extends AbstractChild {

        @Override
        public boolean isExportEnabled() {
            return true;
        }

        @Override
        public Type getType() {
            return Type.TYPE_B;
        }

    }

    public static class Fam {
        private int famId;

        private List<Parent> members;

        public Fam() {
            members = new ArrayList<Parent>();
        }

        public int getFamId() {
            return famId;
        }

        public void setFamId(int famId) {
            this.famId = famId;
        }

        public List<Parent> getMembers() {
            return members;
        }

        public void setMembers(List<Parent> members) {
            this.members = members;
        }

        public void addMember(Parent member) {
            members.add(member);
        }

    }

    public SimpleTestMain() {
    }

    public static void main(String[] args) {
        Fam fam = new Fam();
        FirstChild fc = new FirstChild();
        fc.setId(1);
        fc.setCode("FirstChildCode");
        fc.setMinCount(1);
        fc.setMaxCount(4);

        fam.addMember(fc);

        SecondChild sc = new SecondChild();

        sc.setCode("SecondChildCode");
        sc.setMinCount(131);
        sc.setMaxCount(431);

        fam.addMember(sc);
        String test = "";
        // Serialize it
        ObjectMapper mapper = new ObjectMapper();
        try {
            test = mapper.writeValueAsString(fam);
            System.out.println("Serialized bean:\n" + test);
            // the output
            // Serialized bean:
            // {"famId":0,"members":[{"@cls":".SimpleTestMain$FirstChild","id":1,"code":"FirstChildCode","minCount":1,"maxCount":4,"type":"TYPE_A","exportEnabled":false},{"@cls":".SimpleTestMain$SecondChild","id":0,"code":"SecondChildCode","minCount":131,"maxCount":431,"type":"TYPE_B","exportEnabled":true}]}
        } catch (IOException e) {
            e.printStackTrace();
        }

        // Deserialize it
        mapper = new ObjectMapper();

        //      mapper.enableDefaultTyping();
        try {
            Fam fam1 = mapper.readValue(test, Fam.class);

        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}