根据标识

时间:2016-02-05 15:54:08

标签: java json jackson mixins

我正在尝试反序列化" onclick"包含在"模块中的事件"对象由以下JSON表示:

{
    "parent": {
        "id": 0,
        "children": [{
            "child": {
                "id": 1,
                "description": "A",
                "parent": 0,
                "events": [{
                    "onclick": {
                        "source": 1
                    }
                }]
            }
        }]
    }
}

类结构非常简单:

View (Interface)
 +- AbstractView
    +- Parent
        +- Child

Event (Interface)
 +- AbstractEvent
    +- OnClick

AbstractEvent:

public abstract class AbstractEvent implements Event {

    private View source;

    protected AbstractEvent() {}

    protected AbstractEvent(View source) {
        this.source = source;
    }

    @Override
    public View getSource() {
        return source;
    }

    @Override
    public void setSource(View source) {
        this.source = source;
    }

}

我正在使用Mixins,因为模型用于几个不同的项目。

ViewMixIn:

@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.WRAPPER_OBJECT, property = "type")
@JsonSubTypes({
    @Type(value = Parent.class, name = "parent"),
    @Type(value = Child.class, name = "child")
})
@JsonIdentityInfo(generator = ObjectIdGenerators.PropertyGenerator.class, property = "id")
public abstract class ViewMixIn {

}

EventMixIn:

@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.WRAPPER_OBJECT, property = "class")
@JsonSubTypes({
    @Type(value = OnClick.class, name = "onclick")
})
@JsonIdentityInfo(generator = ObjectIdGenerators.PropertyGenerator.class, property = "source")
public abstract class EventMixIn {

}

SimplifiedModule:

@Override
public void setupModule(SetupContext context) {
    super.setupModule(context);

    context.setMixInAnnotations(AbstractView.class, ViewMixIn.class);
    context.setMixInAnnotations(AbstractEvent.class, EventMixIn.class);

}

ObjectMapper配置:

ObjectMapper mapper = new ObjectMapper();
mapper.registerModule(new SimplifiedModule())
    .setSerializationInclusion(NON_NULL)
    .setSerializationInclusion(NON_EMPTY)
    .enableDefaultTyping()
    .enableDefaultTyping(NON_FINAL, As.WRAPPER_OBJECT)
    .setVisibilityChecker(
        mapper.getSerializationConfig().getDefaultVisibilityChecker()
            .withFieldVisibility(JsonAutoDetect.Visibility.ANY)
            .withGetterVisibility(JsonAutoDetect.Visibility.NONE)
            .withSetterVisibility(JsonAutoDetect.Visibility.NONE)
            .withCreatorVisibility(JsonAutoDetect.Visibility.NONE));

如图所示,模型已正确序列化,但在反序列化期间,我收到以下错误:

  

WARN 11:46:04:949 br.com.pdcore.appmaker.middleware.simplified.SimplifiedModelTest - 无法反序列化Parent。   com.fasterxml.jackson.databind.JsonMappingException:意外的令牌(VALUE_NUMBER_INT),预期的START_OBJECT:需要JSON对象来包含类br.com.pdcore.appmaker.middleware.simplified.model.view.View的As.WRAPPER_OBJECT类型信息    在[来源:{"父母":{" id":0,"孩子":{" java.util.ArrayList":[ {"子" {" ID":1,"描述":" A""父":0 "事件" {"的java.util.ArrayList":[{"的onclick" {"源":1}}]} }},{"子" {" ID":2"描述":" B""父&#34 ;:0,"事件" {"的java.util.ArrayList":[{"的onclick" {"源":2} }]}}},{"子" {" ID":3,"描述":" C""父":0,"事件" {"的java.util.ArrayList":[{"的onclick" {"源" :3}}]}}},{"子" {" ID&#34:4,"描述":" d",& #34;父":0,"事件" {"的java.util.ArrayList":[{"的onclick" {"源& #34:4}}]}}},{"子" {" ID":5,"描述":" E&#34 ;,"父":0,"事件" {"的java.util.ArrayList":[{"的onclick" {&# 34;源":5}}]}}}]}}} ; line:1,column:145](通过参考链:br.com.pdcore.appmaker.middleware.simplified.model.view.Parent [" children"] - > java.util.ArrayList [0 ] - GT; br.com.pdcore.appmaker.middleware.simplified.model.view.Child ["事件"] - > java.util.ArrayList中[0] - > br.com.pdcore .appmaker.middleware.simplified.model.event.OnClick ["源"])

好像不理解"来源" id指的是包装onclick节点的子对象。

如果我更改了MixIn定义:

@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.WRAPPER_OBJECT, property = "name")

为:

@JsonTypeInfo(use = JsonTypeInfo.Id.CLASS, include = JsonTypeInfo.As.PROPERTY, property = "type")

我仍然遇到类似的错误:

  

WARN 12:04:35:126 br.com.pdcore.appmaker.middleware.simplified.SimplifiedModelTest - 无法反序列化Parent。   com.fasterxml.jackson.databind.JsonMappingException:意外的令牌(VALUE_NUMBER_INT),预期的FIELD_NAME:缺少属性' @ class'即包含类型id(对于类br.com.pdcore.appmaker.middleware.simplified.model.view.View)    在[来源:{"类型":" br.com.pdcore.appmaker.middleware.simplified.model.view.Parent"," id":0, "的子":["的java.util.ArrayList",[{"类型":" br.com.pdcore.appmaker.middleware.simplified。 model.view.Child"" ID":1,"描述":" A""父":0,& #34;事件":["的java.util.ArrayList",[{"类型":" br.com.pdcore.appmaker.middleware.simplified.model .event.OnClick""源":1}]]},{"类型":" br.com.pdcore.appmaker.middleware.simplified.model .view.Child"" ID":2"描述":" B""父":0,&# 34;事件":["的java.util.ArrayList",[{"类型":" br.com.pdcore.appmaker.middleware.simplified.model。 event.OnClick""源":2}]]},{"类型":" br.com.pdcore.appmaker.middleware.simplified.model。 view.Child"" ID":3,"描述":" C""父":0,&#34 ;事件":[" java.util.ArrayL IST",[{"类型":" br.com.pdcore.appmaker.middleware.simplified.model.event.OnClick""源&#34 ;: 3}]]},{"类型":" br.com.pdcore.appmaker.middleware.simplified.model.view.Child"" ID&#34 ;: 4,"描述":" d""父":0,"事件":["的java.util.ArrayList& #34;,[{"类型":" br.com.pdcore.appmaker.middleware.simplified.model.event.OnClick""源&#34:4 }]]},{"类型":" br.com.pdcore.appmaker.middleware.simplified.model.view.Child"" ID":5 "描述":" E""父":0,"事件":["的java.util.ArrayList&# 34;,[{"类型":" br.com.pdcore.appmaker.middleware.simplified.model.event.OnClick""源":5} ]]}]]}; line:1,column:331](通过引用链:br.com.pdcore.appmaker.middleware.simplified.model.view.Parent [" children"] - > java.util.ArrayList [0 ] - GT; br.com.pdcore.appmaker.middleware.simplified.model.view.Child ["事件"] - > java.util.ArrayList中[0] - > br.com.pdcore .appmaker.middleware.simplified.model.event.OnClick ["源"])

1 个答案:

答案 0 :(得分:0)

在更仔细地阅读JsonIdentityInfo的javadoc之后,以下确定了问题:

  

在POJO的情况下,必须将对象id序列化为属性;对象标识目前不支持JSON数组类型(Java数组或列表)或Java Map类型。

所以基本上我需要生成一个自定义反序列化器。