CXF:通过现有的 Servlet 传输提供解耦端点

Posted

技术标签:

【中文标题】CXF:通过现有的 Servlet 传输提供解耦端点【英文标题】:CXF: Providing decoupled endpoint via existing Servlet transport 【发布时间】:2011-12-25 02:42:40 【问题描述】:

我有一个使用 CXF 的 Servlet 传输和 Jetty 6.1 提供服务的应用程序。此应用程序还需要使用外部服务。所有服务都支持 WS-Addressing 规范(以及顶部的 WS-RM)。为了使用外部服务,我从应用程序运行生成的服务客户端。

问题在于,当我为客户端提供解耦端点(WS-RM 需要此端点通过单独的 http 连接接收传入消息)时,CXF 运行另一个 Jetty 服务器实例(尽管 Servlet 传输(提供服务)和客户端(使用一些外部服务)共享同一总线)。我不需要两个 Jetty 实例(并不是说它们不能在同一个 HTTP 端口上运行)。

有没有一种方法可以使用现有的 Jetty 服务器和 Servlet 传输来提供解耦端点?

到目前为止,我启用了这样的解耦端点:

Client client = ClientProxy.getClient(port);
HTTPConduit httpConduit = (HTTPConduit) client.getConduit();
httpConduit.getClient().setDecoupledEndpoint(
     "http://domain.com:port/services/dec_endpoints/TestDecEndpoint");

如果我提供相对路径(“/dec_endpoints/TestDecEndpoint”,就像通过 Servlet 传输提供服务时使用相对路径一样),HTTP 管道不会在 SOAP 消息的标头中指定完整路径,因此这不会也可以工作(服务器无法向 /dec_endpoints/TestDecEndpoint 发送消息)。

【问题讨论】:

【参考方案1】:

好的,我自己找到了解决方案。您需要为解耦端点指定相对路径并手动更改消息的寻址属性(在 MAPAggregator 拦截器之后,因为它设置了解耦目的地),以便服务器可以向您的地址发送回复。

所以我们有什么:

    使用相对路径解耦目的地:/dec_endpoints/SomeDestination <ReplyTo> 带有绝对路径的标头:http://addr.com:port/servlet_path/dec_endpoints/SomeDestination

以下是如何更改路径的示例:

public class ReplyToInterceptor extends AbstractPhaseInterceptor<Message>

    public ReplyToInterceptor() 
        super(Phase.PRE_LOGICAL);
        addAfter(MAPAggregator.class.getName());
    

    public void handleMessage(Message message) 
        AddressingProperties maps = ContextUtils.retrieveMAPs(message, false, 
           true);
        EndpointReferenceType replyTo = maps.getReplyTo();
        replyTo.getAddress().setValue(
           "http://address.com:port/servlet_path/dec_endpoints/SomeDestination");
    

【讨论】:

以上是关于CXF:通过现有的 Servlet 传输提供解耦端点的主要内容,如果未能解决你的问题,请参考以下文章

使用servlet传输Jboss fuse 6.3公开https camel cxf webservice

SpringBoot Spring Cloud 整合cxf开发webService接口服务端-流程步骤

Web Service 实现之CXF

使用CXF做webservice整合现有项目的例子

Undertow:使用现有的 Servlet 实例

解决web浏览器与servlet之间传输数据时出现的乱码问题