无法使用(de)序列化具有Jackson中多态项的List [英] Cannot with (de)serialize a List with polymorphic items in Jackson

查看:157
本文介绍了无法使用(de)序列化具有Jackson中多态项的List的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个问题(de)序列化我没有定义的JSON。

I have an issue (de)serializing JSON that is not defined by me.

以下是一些解释此问题的代码和JSON:

Here is some code and JSON that explains the issue:

代码:

public static class Base {
    public String klass = "base";
}

public static class SubBase extends Base {
}

public static class Sub1 extends SubBase {
    public Sub1() {
        klass = "Sub1";
    }
}

public static class Sub2 extends SubBase {
    public Sub2() {
        klass = "Sub2";
    }
}

public static class Holder {
    @JsonTypeInfo(use=JsonTypeInfo.Id.NAME, include=JsonTypeInfo.As.WRAPPER_ARRAY, property="type")
    @JsonSubTypes({@JsonSubTypes.Type (name = "sub1", value = Sub1.class),@JsonSubTypes.Type(name = "sub2", value = Sub2.class)})
    public List<Base> items = new ArrayList<Base>();
}


Holder holder = new Holder();
holder.items.add(new Sub1());
holder.items.add(new Sub1());

mapper.writeValueAsString(holder);

产生

{"items":[["sub1",{"klass":"Sub1"}],["sub1",{"klass":"Sub1"}]]}

如果我将JsonTypeInfo注释更改为

If I change the JsonTypeInfo annotation to

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

产生

{"items":[{"sub1":{"klass":"Sub1"}},{"sub1":{"klass":"Sub1"}}]}

到目前为止,一切都很好:)

So far, all is good :)

但是,我从服务器获得的JSON结构略有不同:

However, the JSON I'm getting from the server has a slightly different structure:

{"type":"sub1", "items":[{"klass":"Sub1"},{"klass":"Sub1"}]}

在type属性中定义items数组的类型(请注意,所有项目都在items数组属于同一类。)
我无法弄清楚使用哪个JsonTypeInfo组合来实现这一点。我尝试将'include'设置为.EXTERNAL_PROPERTY,但这不起作用。

使用此包含进行反序列化会给我线程中的异常mainorg.codehaus.jackson.JsonGenerationException :无法写入字段名称,期望值错误消息。

Where the type of the items array is defined in the "type" property (note that all items in the "items" array are of the same class).
I just cannot figure out which JsonTypeInfo combination to use to make this happen. I tried setting the 'include' to ".EXTERNAL_PROPERTY", but this doesn't work.
Deserializing using this inclusion gives me "Exception in thread "main" org.codehaus.jackson.JsonGenerationException: Can not write a field name, expecting a value" error message.

我的问题是:我需要使用哪个注释以便' {type:sub1,items:[{klass:Sub1},{klass:Sub1}}} '将填充'items'数组Sub1实例基于Holder的 type 属性?

如果这是不可能的,还有另一种方法可以实现这一点(不需要自定义序列化器Holder;只为'items'数组的自定义序列化器会没问题?

My question is: Which annotation do I need to use so that '{"type":"sub1", "items":[{"klass":"Sub1"},{"klass":"Sub1"}]}' will fill the 'items' array with all Sub1 instances based on the "type" property of the Holder?
If this is just not possible, is there another way to accomplish this (without the need of an custom serializer for Holder; a custom serializer just for the 'items' array would be fine)?

谢谢!

推荐答案

无法映射JSON你自动显示;它不是Jackson支持的4种类型之一。

There is no way to map JSON you show automatically; it is not one of 4 types supported by Jackson.

如果你不能让服务器产生更多标准结构(存在自动支持),你需要写自定义反序列化器;或者分两步进行数据绑定,首先进入一个中间易于映射的结构(如 JsonNode Map )和然后从那里进入所需的结构手动提取类型,使用它(例如,使用 ObjectMapper.convertValue(object,resultType)

If you can't make server produce more standard structure (for which automatic support exists), you will need to write a custom deserializer; or to do data-binding in two steps, first into an intermediate easily mappable structure (like JsonNode or Map) and then from that into desired structure manually extracting type, using that (for example, with ObjectMapper.convertValue(object, resultType).

这篇关于无法使用(de)序列化具有Jackson中多态项的List的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆