CXF @PUT 请求 "No message body writer has been found" 异常
CXF @PUT request "No message body writer has been found" exception
我完全卡住了!花了很多时间在这上面没有任何进展...
我有一个带有 CXF 3 (3.1.4) 的 Spring 4 (4.2.3.RELEASE) 应用程序,我正在尝试对其进行 JUnit 测试。除了 PUT 请求外,一切都运行良好。我收到以下错误:
Caused by: org.apache.cxf.interceptor.Fault: No message body writer has been found for class com.someproject.logic.api.data.User, ContentType: application/xml
at org.apache.cxf.jaxrs.client.WebClient$BodyWriter.doWriteBody(WebClient.java:1222)
at org.apache.cxf.jaxrs.client.AbstractClient$AbstractBodyWriter.handleMessage(AbstractClient.java:1091)
at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:308)
at org.apache.cxf.jaxrs.client.AbstractClient.doRunInterceptorChain(AbstractClient.java:649)
at org.apache.cxf.jaxrs.client.WebClient.doChainedInvocation(WebClient.java:1093)
... 49 more
原因:javax.ws.rs.ProcessingException:未找到 class com.someproject.logic.api.data.User 的邮件正文作者,ContentType:application/xml
在 org.apache.cxf.jaxrs.client.AbstractClient.reportMessageHandlerProblem(AbstractClient.java:780)
在 org.apache.cxf.jaxrs.client.AbstractClient.writeBody(AbstractClient.java:494)
在 org.apache.cxf.jaxrs.client.WebClient$BodyWriter.doWriteBody(WebClient.java:1217)
... 还有 53 个
我也试过 "application/json" 得到了同样的结果。
这是 CXF 配置:
@Bean
@DependsOn("cxf")
public Server jaxRsServer() {
JAXRSServerFactoryBean sf = new JAXRSServerFactoryBean();
List<Object> providers = new ArrayList<Object>();
// get all the class annotated with @JaxrsService
List<Object> beans = configUtil.findBeans(JaxrsService.class);
if (beans.size() > 0) {
// add all the CXF service classes into the CXF stack
sf.setServiceBeans(beans);
sf.setAddress("http://localhost:8080/api");
sf.setBus(springBus);
sf.setStart(true);
// set JSON as the response serializer
JacksonJsonProvider provider = new JacksonJsonProvider();
providers.add( provider );
}
// add custom providers if any
sf.setProviders(providers);
return sf.create();
}
端点:
@Path("/user")
@PUT
@Consumes({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON, })
@Produces( MediaType.APPLICATION_JSON )
public User updateUser( User user );
端点实现:
@Override
public User updateUser( User user ) {
System.out.println( "updateUser: " + user );
return user;
}
测试:
@Before
public void setUp() throws Exception {
MockitoAnnotations.initMocks(this);
webClient = WebClient.create( "http://localhost:8080/api" );
WebClient.getConfig( webClient ).getRequestContext().put( LocalConduit.DIRECT_DISPATCH, Boolean.TRUE );
webClient.accept( "application/json" );
}
@Test
public void testPut() {
String apiUrl = "/user";
webClient.path( apiUrl );
User user = createDummyAPIUser();
try {
System.out.println( "testUpdateUser: PUT request to " + apiUrl );
String response = webClient.type( MediaType.APPLICATION_JSON ).put( user, String.class );
System.out.println( "testUpdateUser: " + apiUrl + " response: " + response );
//updatedUser = (new ObjectMapper()).readValue( response, User.class );
} catch( Exception e ) {
e.printStackTrace();
fail();
return;
}
}
首先,我如何确保 fasterxml Jackson 2 提供程序实际上正在序列化消息正文?它在堆栈跟踪中看不到 Jackson 的任何内容,但我确实在提供程序中设置了它。
我发现这个 link 用于演示自定义 ContextProvider,这是让它工作的唯一方法吗?看起来完全多余...
http://www.blackpepper.co.uk/custom-context-providers-for-cxf-with-the-context-annotation/
有什么想法吗?
谢谢!!
GEEEEEEZZZ...
感觉像个笨蛋,忘了给客户端添加相同的 Jackson 序列化程序(提供程序)。再次查看堆栈跟踪,我注意到这些方法仅来自客户端,因此显然客户端不知道如何使用我向其抛出的 POJO...
更新测试代码:
@Before
public void setUp() throws Exception {
MockitoAnnotations.initMocks(this);
final List<Object> providers = new ArrayList<Object>();
JacksonJaxbJsonProvider jacksonJsonProvider = new JacksonJaxbJsonProvider();
providers.add( jacksonJsonProvider );
webClient = WebClient.create( "http://localhost:8080/api", providers );
WebClient.getConfig( webClient ).getRequestContext().put( LocalConduit.DIRECT_DISPATCH, Boolean.TRUE );
webClient.accept( "application/json" );
}
我完全卡住了!花了很多时间在这上面没有任何进展...
我有一个带有 CXF 3 (3.1.4) 的 Spring 4 (4.2.3.RELEASE) 应用程序,我正在尝试对其进行 JUnit 测试。除了 PUT 请求外,一切都运行良好。我收到以下错误:
Caused by: org.apache.cxf.interceptor.Fault: No message body writer has been found for class com.someproject.logic.api.data.User, ContentType: application/xml
at org.apache.cxf.jaxrs.client.WebClient$BodyWriter.doWriteBody(WebClient.java:1222)
at org.apache.cxf.jaxrs.client.AbstractClient$AbstractBodyWriter.handleMessage(AbstractClient.java:1091)
at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:308)
at org.apache.cxf.jaxrs.client.AbstractClient.doRunInterceptorChain(AbstractClient.java:649)
at org.apache.cxf.jaxrs.client.WebClient.doChainedInvocation(WebClient.java:1093)
... 49 more
原因:javax.ws.rs.ProcessingException:未找到 class com.someproject.logic.api.data.User 的邮件正文作者,ContentType:application/xml 在 org.apache.cxf.jaxrs.client.AbstractClient.reportMessageHandlerProblem(AbstractClient.java:780) 在 org.apache.cxf.jaxrs.client.AbstractClient.writeBody(AbstractClient.java:494) 在 org.apache.cxf.jaxrs.client.WebClient$BodyWriter.doWriteBody(WebClient.java:1217) ... 还有 53 个
我也试过 "application/json" 得到了同样的结果。
这是 CXF 配置:
@Bean
@DependsOn("cxf")
public Server jaxRsServer() {
JAXRSServerFactoryBean sf = new JAXRSServerFactoryBean();
List<Object> providers = new ArrayList<Object>();
// get all the class annotated with @JaxrsService
List<Object> beans = configUtil.findBeans(JaxrsService.class);
if (beans.size() > 0) {
// add all the CXF service classes into the CXF stack
sf.setServiceBeans(beans);
sf.setAddress("http://localhost:8080/api");
sf.setBus(springBus);
sf.setStart(true);
// set JSON as the response serializer
JacksonJsonProvider provider = new JacksonJsonProvider();
providers.add( provider );
}
// add custom providers if any
sf.setProviders(providers);
return sf.create();
}
端点:
@Path("/user")
@PUT
@Consumes({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON, })
@Produces( MediaType.APPLICATION_JSON )
public User updateUser( User user );
端点实现:
@Override
public User updateUser( User user ) {
System.out.println( "updateUser: " + user );
return user;
}
测试:
@Before
public void setUp() throws Exception {
MockitoAnnotations.initMocks(this);
webClient = WebClient.create( "http://localhost:8080/api" );
WebClient.getConfig( webClient ).getRequestContext().put( LocalConduit.DIRECT_DISPATCH, Boolean.TRUE );
webClient.accept( "application/json" );
}
@Test
public void testPut() {
String apiUrl = "/user";
webClient.path( apiUrl );
User user = createDummyAPIUser();
try {
System.out.println( "testUpdateUser: PUT request to " + apiUrl );
String response = webClient.type( MediaType.APPLICATION_JSON ).put( user, String.class );
System.out.println( "testUpdateUser: " + apiUrl + " response: " + response );
//updatedUser = (new ObjectMapper()).readValue( response, User.class );
} catch( Exception e ) {
e.printStackTrace();
fail();
return;
}
}
首先,我如何确保 fasterxml Jackson 2 提供程序实际上正在序列化消息正文?它在堆栈跟踪中看不到 Jackson 的任何内容,但我确实在提供程序中设置了它。
我发现这个 link 用于演示自定义 ContextProvider,这是让它工作的唯一方法吗?看起来完全多余... http://www.blackpepper.co.uk/custom-context-providers-for-cxf-with-the-context-annotation/
有什么想法吗?
谢谢!!
GEEEEEEZZZ...
感觉像个笨蛋,忘了给客户端添加相同的 Jackson 序列化程序(提供程序)。再次查看堆栈跟踪,我注意到这些方法仅来自客户端,因此显然客户端不知道如何使用我向其抛出的 POJO...
更新测试代码:
@Before
public void setUp() throws Exception {
MockitoAnnotations.initMocks(this);
final List<Object> providers = new ArrayList<Object>();
JacksonJaxbJsonProvider jacksonJsonProvider = new JacksonJaxbJsonProvider();
providers.add( jacksonJsonProvider );
webClient = WebClient.create( "http://localhost:8080/api", providers );
WebClient.getConfig( webClient ).getRequestContext().put( LocalConduit.DIRECT_DISPATCH, Boolean.TRUE );
webClient.accept( "application/json" );
}