Web Services CXF在加载WSDL时启用GZIP失败

olmpazwi  于 2022-11-15  发布在  其他
关注(0)|答案(1)|浏览(136)

我目前在尝试为CXF启用GZIP压缩时遇到问题:WSDL加载失败,因为它是压缩的,而客户端部分没有对其进行解压缩。
这意味着比我在做以下事情时:

persistenceService = Service.create(
                                new URL(replaceHostAndPort(
                                        getClientServiceConfiguration().getWsMetadataPersistenceService())),
                                new QName("http://metadata.ws.com", "WsMetadataPersistenceService"), gzipFeature);
                        mDefaultMetadataPersistence = persistenceService.getPort(IWsMetadataPersistence.class);

代码在Service.create()上失败,因此它与配置ClientProxy无关。
就我在CFX的源代码中所知,WSDL的加载没有使用我在参数中传递的特性,也没有使用我使用以下配置在默认总线上传递的特性:

<bean id="compressGZIPFeature" class="org.apache.cxf.transport.common.gzip.GZIPFeature"/> 
<cxf:bus>
    <cxf:features>
         <ref bean="compressGZIPFeature"/>        
    </cxf:features>
</cxf:bus>

注意:我可以在使用总线元素的CXF内部类所使用的总线示例中看到,我的特性在那里,并且被正确初始化(添加入/出拦截器),但是当尝试加载WSDL文件时,我从来没有使用它们。
现在我有点卡住了:WSDL一开始就不应该被gzip压缩吗?2那为什么会这样呢?3还是我的问题出在客户端?
在服务器端,我尝试了各种可能的组合,希望只压缩请求的内容,而不压缩WSDL,但没有效果:

  • @邮政编码
  • XML总线配置
  • @输入/输出拦截器

根据我对CXF客户端代码的理解,HttpUrlConnection的InputStream直接传递给XMLReader来读取WSDL,而不使用拦截器(此外,GZIPInterceptor忽略来自GET请求的消息,因此它应该忽略GET [...]?wsdl。如果您想检查代码,请参阅WSDLManagerImpl.loadDefinition()。
我不确定它是否相关,我正在采用openjdk 8和cxf 3.1.7。

pokxtpni

pokxtpni1#

我找到了解决办法:我在HTTPConduit上添加了压缩,这甚至会使wsdl请求请求GZIP版本。问题是WSDL读取器不处理收到的GZIP流。
因此,我必须删除客户端上的压缩配置,并使用以下代码确保只压缩SOAP请求:

public <T> T createAndConfigureService(Class<? extends T> theServiceClass, Service service){
    T theWebService = service.getPort(theServiceClass);
    Map<String, Object> requestHeaders = new HashMap<>();
    requestHeaders.put("Accept-Encoding", new ArrayList<>(Arrays.asList("gzip")));
    ((BindingProvider)theWebService).getRequestContext().put(MessageContext.HTTP_REQUEST_HEADERS, requestHeaders);
    Client client = ClientProxy.getClient(theWebService); 
    client.getInInterceptors().add(new GZIPInInterceptor());
    return theWebService;
}

相关问题