即使添加了Object Mapper,Jackson也无法检测到JAXB注释

时间:2013-04-09 16:28:48

标签: json jaxb jackson

我正在尝试使用带有JaxB @XmlRootElement注释的CXF + Jackson配置REST服务的简单示例。我已经在堆栈溢出以及像this这样的博客中遇到了各种类似的问题,并提出了以下解决方案:

按如下方式创建自定义对象映射器:

public class CustomObjectMapper extends ObjectMapper{

    public CustomObjectMapper() {
    super();
    super.configure(SerializationConfig.Feature.WRAP_ROOT_VALUE, true);
    super.setSerializationInclusion(JsonSerialize.Inclusion.NON_NULL);
    AnnotationIntrospector primary = new JaxbAnnotationIntrospector();
    AnnotationIntrospector secondary =  new JacksonAnnotationIntrospector();
    AnnotationIntrospector pair = new AnnotationIntrospector.Pair(primary, secondary);
    super.setAnnotationIntrospector(pair);
    }

}

在Spring config

中将此传递给Json提供的构造函数
  <bean id="jacksonMapper" class="com.myorg.test.CustomObjectMapper" />

    <jaxrs:providers>
        <bean class="org.codehaus.jackson.jaxrs.JacksonJsonProvider">
            <constructor-arg ref="jacksonMapper" />
        </bean>
    </jaxrs:providers>

添加了一个带有JAXB根元素注释的简单类JsonBean

@XmlRootElement(name = "JsonBean")
public class JsonBean {
    private String val1;
    private String val2;

    public String getVal1() {
        return val1;
    }

    public void setVal1(String val1) {
        this.val1 = val1;
    }

    public String getVal2() {
        return val2;
    }

    public void setVal2(String val2) {
        this.val2 = val2;
    }

}

当我通过下面的json时,

{
    "JsonBean": {
        "val1": "Hello",
        "val2": "Hi"
    }
}

它抛出异常:

WARNING: javax.ws.rs.InternalServerErrorException: org.codehaus.jackson.map.exc.UnrecognizedPropertyException: Unrecognized field "JsonBean" (Class com.cognizan
t.poc.connectedcar.JsonBean), not marked as ignorable
 at [Source: org.apache.cxf.transport.http.AbstractHTTPDestination$1@1f2fae4; line: 2, column: 13] (through reference chain: com.myorg.test.Json
Bean["JsonBean"])
        at org.apache.cxf.jaxrs.interceptor.JAXRSInInterceptor.processRequest(JAXRSInInterceptor.java:243)
        at org.apache.cxf.jaxrs.interceptor.JAXRSInInterceptor.handleMessage(JAXRSInInterceptor.java:99)
        at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:271)
        at org.apache.cxf.transport.ChainInitiationObserver.onMessage(ChainInitiationObserver.java:121)
        at org.apache.cxf.transport.http.AbstractHTTPDestination.invoke(AbstractHTTPDestination.java:239)
        at org.apache.cxf.transport.servlet.ServletController.invokeDestination(ServletController.java:223)
        at org.apache.cxf.transport.servlet.ServletController.invoke(ServletController.java:203)
        at org.apache.cxf.transport.servlet.ServletController.invoke(ServletController.java:137)
        at org.apache.cxf.transport.servlet.CXFNonSpringServlet.invoke(CXFNonSpringServlet.java:158)
        at org.apache.cxf.transport.servlet.AbstractHTTPServlet.handleRequest(AbstractHTTPServlet.java:243)
        at org.apache.cxf.transport.servlet.AbstractHTTPServlet.doPost(AbstractHTTPServlet.java:163)
        at javax.servlet.http.HttpServlet.service(HttpServlet.java:755)
        at org.apache.cxf.transport.servlet.AbstractHTTPServlet.service(AbstractHTTPServlet.java:219)
        at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:669)
        at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:457)
        at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:137)
        at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:557)
        at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:231)
        at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1075)
        at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:384)
        at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:193)
        at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1009)
        at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:135)
        at org.eclipse.jetty.server.handler.ContextHandlerCollection.handle(ContextHandlerCollection.java:255)
        at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerCollection.java:154)
        at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:116)
        at org.eclipse.jetty.server.Server.handle(Server.java:368)
        at org.eclipse.jetty.server.AbstractHttpConnection.handleRequest(AbstractHttpConnection.java:489)
        at org.eclipse.jetty.server.AbstractHttpConnection.content(AbstractHttpConnection.java:953)

我在这里遗漏了什么吗?请帮忙。

1 个答案:

答案 0 :(得分:2)

我做对了。

我错过了在自定义映射器中为反序列化添加解包:

CustomObjectMaller

中添加了以下行
super.configure(DeserializationConfig.Feature.UNWRAP_ROOT_VALUE, true);

另外,将spring配置文件修改为:

<jaxrs:providers>
    <bean id="jsonProvider" class="org.codehaus.jackson.jaxrs.JacksonJaxbJsonProvider">
       <property name="mapper" ref="jacksonMapper" />
   </bean>
</jaxrs:providers>

它开始按预期工作..