我在使用Apache CXF生成的类(wsdl2java)访问Web服务时遇到问题。
一切正常,直到网络服务提供商突然改变他们的防火墙规则并给我们打了个电话。他们所说的是他们不再允许 http 流量,我们必须开始使用 https 。有趣的是,到目前为止,我们认为 使用https。这是继承的遗留代码。但我们几乎在Apache CXF网站上逐字逐句地使用ssl示例。
这是wsdl的一大块:
...
<wsdl:portType name="GetMessagesSoap">
<wsdl:operation name="GetInfo">
<wsdl:input message="tns:GetInfoSoapIn" />
<wsdl:output message="tns:GetInfoSoapOut" />
</wsdl:operation>
</wsdl:portType>
...
<wsdl:service name="GetMessages">
<wsdl:port name="GetMessagesSoap" binding="tns:GetMessagesSoap">
<soap:address location="http://127.0.0.1/GetMessages.asmx" />
</wsdl:port>
</wsdl:service>
基本上我们使用wsdl2java生成所有Java类。然后在我们的Gateway类中,我们执行以下操作:
private GetMessagesSoap getInstance() {
GetMessages getMessages = new GetMessages(wsdlUrl);
GetMessagesSoap getMessagesSoap = getMessages.getMessagesSoap();
setupTransportLayerSecurity(getMessagesSoap);
}
private void setupTransportLayerSecurity(final Object port) {
HTTPConduit httpConduit =
(HTTPConduit) ClientProxy.getClient(port).getConduit();
TLSClientParameters tlsCP = new TLSClientParameters();
KeyStore keyStore = ...
KeyManager[] myKeyManagers = getKeyManagers(keyStore ...
tlsCP.setKeyManagers(myKeyManagers);
KeyStore trustStore = ...
TrustManager[] myTrustStoreKeyManagers = getTrustManagers(trustStore);
tlsCP.setTrustManagers(myTrustStoreKeyManagers);
tlsCP.setDisableCNCheck(true);
tlsCP.setSecureSocketProtocol("SSL");
httpConduit.setTlsClientParameters(tlsCP);
}
然后我们调用getInfo()。这是发生错误的地方。
public void getInfo() {
GetMessagesSoap getMessagesSoap = getInstance();
InfoResponse response = getMessagesSoap.getInfo()
}
我们得到的错误非常通用:
javax.xml.ws.WebServiceException: Could not send Message.
ws提供商表示它失败了,因为我们正试图使用http。所有这些尽管我们在setupTransportLayerSecurity()方法中做了很多花哨的SSL。
我对这一切的根本怀疑是,它真的是失败的原因吗?我的意思是,当规则从防火墙中删除时,显然它开始失败。但是,我不明白的是,如果wsdl中GetMessages服务中的url是http,即使我说要使用SSL,世界上它将如何使用https?
我们在网络上放了一个嗅探器,果然它只使用http。但是......这不是正常的吗?显然,我绝不是SOAP专家。有人能解释一下这个问题吗?
答案 0 :(得分:0)
当地址网址以https开头时,CXF HttpConduit仅使用TlsClientParameters。 你能改变WSDL文件吗? 如果没有,您可以change service url at the runtime。