论坛首页 Java版

解决Apache CXF 发送soap请求时由于缺少content-length带来的问题

浏览 499 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
时间:2007-11-23 关键字: SOA CXF Spring

(1) spring配置文件

〈beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:simple="http://cxf.apache.org/simple"
xsi:schemaLocation="
http://cxf.apache.org/simple http://cxf.apache.org/schemas/simple.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.0.xsd">

〈simple:client id="userService" serviceClass="xxxx.UserService"
address="http://xxxx/UserService">
〈/simple:client>

〈beans>

(2)客户端代码
ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath*:xxxx/spring*.xml");
UserService userService = (UserService) ctx.getBean("userService");
userService.xxxxx(xxxx);


如上所示,使用simple frontend方式(org.apache.cxf.frontend.ClientFactoryBean)对apache cxf提供的webservices进行调用,将apache cxf服务端由测试环境迁移至lighttpd + tomcat的生产环境后程序运行报错。

使用apache soap2.3提供的TcpTunnenGui工具对soap包进行了抓取:

client发送的soap请求格式大致为
POST xxx HTTP/1.1
xxxxx
。。。。

在包头中没有content-length字样

lighttpd 返回"411 Length require"字样的错误。同时,在lighttpd的err日志里面,有如下的错误信息
2007-09-27 16:17:39: (request.c.1110) POST-request, but content-length
missing -> 411
如何才能使cxf client发送的soap请求信息中包含content-length信息呢?

根据 http://issues.apache.org/jira/browse/CXF-945http://cwiki.apache.org/CXF20DOC/client-http-transport.html 等文章的描述,大致有两种解决办法。

解决办法一:
在cfx.xml 配置文件中做如下配置
〈beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:http-conf="http://cxf.apache.org/transports/http/configuration"
xsi:schemaLocation="http://cxf.apache.org/transports/http/configuration
http://cxf.apache.org/schemas/configuration/http-conf.xsd
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">

〈http-conf:conduit name="{urn:ebay:apis:eBLBaseComponents}Shopping.http-conduit">
〈http-conf:client AllowChunking="false"/>
〈/http-conf:conduit>
〈/beans>

注:此种解决方法在我的测试中未通过(有可能是个人的配置不正确)

解决方法二:
SOAPService service = new SOAPService(wsdl, serviceName);
Greeter greeter = service.getPort(bethalQ, Greeter.class);

Client client = ClientProxy.getClient(greeter);
HTTPConduit http = (HTTPConduit) client.getConduit();
HTTPClientPolicy httpClientPolicy = http.getClient();
httpClientPolicy.setAllowChunking(false);
此方法经测试能解决问题,但总觉得不太合个人味口,难不成客户端调用的时候每次都这么折腾一大堆吧?

我的解决方法:
1、自定义了一个ConduitSelector,代码如下:
public class HttpConduitSelector extends DeferredConduitSelector {

/**
* overriding methods
* (non-Javadoc)
* @see org.apache.cxf.endpoint.DeferredConduitSelector#selectConduit(org.apache.cxf.message.Message)
*/
public Conduit selectConduit(Message message) {
Conduit c = getSelectedConduit(message);
if (c instanceof HTTPConduit) {
HTTPClientPolicy httpClientPolicy = ((HTTPConduit) c).getClient();
httpClientPolicy.setAllowChunking(false);
}
return c;
}

}
2、修改spring配置文件

〈beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:simple="http://cxf.apache.org/simple"
xsi:schemaLocation="
http://cxf.apache.org/simple http://cxf.apache.org/schemas/simple.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.0.xsd">

〈simple:client id="userService" serviceClass="xxxx.UserService"
address="http://xxxx/UserService">
〈simple:conduitSelector>
〈bean class="xxxx.HttpConduitSelector" />
〈/simple:conduitSelector>

〈/simple:client>

〈beans>




   
时间:2008-03-04
在CXF中你可以使用 通配符*来配置多个HttpConduit,解决方法一可以改成
<beans xmlns="http://www.springframework.org/schema/beans"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xmlns:sec="http://cxf.apache.org/configuration/security"
  xmlns:http="http://cxf.apache.org/transports/http/configuration"
  xmlns:jaxws="http://java.sun.com/xml/ns/jaxws"
  xsi:schemaLocation="
  		   http://cxf.apache.org/configuration/security
  		      http://cxf.apache.org/schemas/configuration/security.xsd
           http://cxf.apache.org/transports/http/configuration
              http://cxf.apache.org/schemas/configuration/http-conf.xsd
           http://www.springframework.org/schema/beans
              http://www.springframework.org/schema/beans/spring-beans-2.0.xsd">

<http:conduit name="*.http-conduit">
<http:client AllowChunking="false">
</http:conduit>
</beans>
   
0 请登录后投票
论坛首页 Java版

跳转论坛:
JavaEye推荐