如何使用Jersey将嵌套列表编组为JSON?我得到一个空数组或一个包含数组的单元素字典数组

8 java arrays json jaxb jersey

我正在开发一个使用Jersey将对象转换为JSON的项目.我希望能够写出嵌套列表,如下所示:

{"data":[["one", "two", "three"], ["a", "b", "c"]]}
Run Code Online (Sandbox Code Playgroud)

我想要转换的对象首先将数据表示为<LinkedList <LinkedList <String >>>,我认为Jersey会做正确的事情.以上输出为空值列表:

{"data":[null, null]}
Run Code Online (Sandbox Code Playgroud)

在阅读了需要包装的嵌套对象之后,我尝试了以下方法:

@XmlRootElement(name = "foo")
@XmlType(propOrder = {"data"})
public class Foo
{
    private Collection<FooData> data = new LinkedList<FooData>();

    @XmlElement(name = "data")
    public Collection<FooData> getData()
    {
        return data;
    }

    public void addData(Collection data)
    {
        FooData d = new FooData();
        for(Object o: data)
        {
            d.getData().add(o == null ? (String)o : o.toString());
        }
        this.data.add(d);
    }

    @XmlRootElement(name = "FooData")
    public static class FooData
    {
        private Collection<String> data = new LinkedList<String>();

        @XmlElement
        public Collection<String> getData()
        {
            return data;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

该代码输出下面的内容,这更接近我想要的内容:

{"data":[{"data":["one", "two", "three"]},{"data":["a", "b", "c"]}]}
Run Code Online (Sandbox Code Playgroud)

我希望第一个数据是列表列表,而不是单元素字典列表.我该如何实现这一目标?

这是我的JAXBContentResolver:

@Provider
public class JAXBContextResolver implements ContextResolver<JAXBContext>
{
    private JAXBContext context;
    private Set<Class<?>> types;

    // Only parent classes are required here. Nested classes are implicit.
    protected Class<?>[] classTypes = new Class[] {Foo.class};

    protected Set<String> jsonArray = new HashSet<String>(1) {
        {
            add("data");
        }
    };

    public JAXBContextResolver() throws Exception
    {        
        Map<String, Object> props = new HashMap<String, Object>();
        props.put(JSONJAXBContext.JSON_NOTATION, JSONJAXBContext.JSONNotation.MAPPED);
        props.put(JSONJAXBContext.JSON_ROOT_UNWRAPPING, Boolean.TRUE);
        props.put(JSONJAXBContext.JSON_ARRAYS, jsonArray);
        this.types = new HashSet<Class<?>>(Arrays.asList(classTypes));
        this.context = new JSONJAXBContext(classTyes, props);
    }

    public JAXBContext getContext(Class<?> objectType)
    {
        return (types.contains(objectType)) ? context : null;
    }
}
Run Code Online (Sandbox Code Playgroud)

小智 5

你试过jersey-json吗?

将jersey-json添加到您的类路径(或您的maven依赖项)

然后用这个:

@Provider
public class JAXBContextResolver implements ContextResolver<JAXBContext> {

    private final JAXBContext context;

    public JAXBContextResolver() throws Exception {
        this.context = new JSONJAXBContext(JSONConfiguration.natural().build(), "package.of.your.model");
    }

    public JAXBContext getContext(Class<?> objectType) {
        return context;
    }

}
Run Code Online (Sandbox Code Playgroud)

你只需要在你的资源中使用这样的东西(假设DetailProduit是你要序列化的对象,而且DetailProduit.java是jaxb标记的,并且在package.of.your.model中)

@GET
@Produces(MediaType.APPLICATION_JSON)
@Path("/{code}")
public DetailProduit getDetailProduit(@PathParam("code") String code) {
        .... Your Code ........
    }
Run Code Online (Sandbox Code Playgroud)