I am a client to a SOAP service I do not control (implemented in .NET). The service provides a WSDL. I use Apache CXF to generate the java client from the WSDL (specifically, I
Finally found the correct solution:
You're missing a dependency that provides an implementation of PolicyAssertionValidator
to validate a policy of the name {http://schemas.xmlsoap.org/ws/2005/07/securitypolicy}TransportBinding
.
The correct dependency to use is org.glassfish.metro:wssx-impl. This library provides a class called SecurityPolicyValidator
that can validate said policy. The library will work automatically just by putting it on your classpath.
This solution should work with both the JAX-WS stack and Apache CXF.
Through guesswork and looking at artifacts in maven central, I was able to hit upon a solution.
It turns out that in order to actually understand and evaluate the policy in this wsdl, a missing runtime dependency must be provided. For me it was org.apache.cxf/cxf-rt-frontend-jaxws. I could not find this documented anywhere. This pulls in a number of other cxf dependencies and I don't know if a more minimal set of them is ok.
Once I include this dependency, I no longer get a warning when I instantiate the client object. (Also, instantiation takes much longer!)
However, when I try to use the service I get an exception:
javax.xml.ws.soap.SOAPFaultException: None of the policy alternatives can be satisfied.
at org.apache.cxf.jaxws.JaxWsClientProxy.invoke(JaxWsClientProxy.java:159)
...
This is most likely for the reason that Willie Wheeler's answer pointed out: the policy requires 256 bit encryption on the transport, but this service's SSL is using 128 bit encryption. However, using a wsdl with Base128
instead does not resolve this exception and I did not investigate further.
So it's quite possible that everyone who uses this service probably gets this warning or something like it, and it's impossible to use this service if the security policy is actually checked. I guess I will be living with the warning instead.
I can reproduce this issue with the Express-1 label service:
2014-09-10 22:15:29.601 WARN 6564 --- [ main] c.s.x.i.w.w.EffectiveAlternativeSelector : WSP0075: Policy assertion "{http://schemas.xmlsoap.org/ws/2005/07/securitypolicy}TransportBinding" was evaluated as "UNKNOWN".
2014-09-10 22:15:29.602 WARN 6564 --- [ main] c.s.x.i.w.w.EffectiveAlternativeSelector : WSP0019: Suboptimal policy alternative selected on the client side with fitness "UNKNOWN".
I believe the problem is that the policy you inline above requires Basic256 message encryption, but the service's SSL encryption is weaker.
For example, check out this WSDL:
https://service.express1.com/Services/EwsLabelService.svc?wsdl
At the very top you will see a policy identical to the one you give. But then if you look at the site's SSL cert, it is using AES_128_CBC, which is only 128-bit encryption.
See http://specs.xmlsoap.org/ws/2005/07/securitypolicy/ws-securitypolicy.pdf, sections 7.1, 8.1 and 8.3 for information about TransportBinding policies and algorithm suites. I believe that the warning is saying is that the policy requires 256-bit encryption, but because the service doesn't support it, the client is choosing a weaker encryption algorithm in its place.
As this is a problem on the service side, probably the best way to fix it is to notify the party responsible for the service of the issue.
I found that these errors are being logged BEFORE the SOAP request is even sent.
The warnings did not appear in Java 6. They do appear in Java 7 and Java 8. My hunch is that these warnings are related to the legacy jaxrpc.jar in my source code.
My "hack" work-around was to download a copy of the WSDL file and modify the policy section. Then point the main class in my web-service to this modified WSDL file.
//Modified tags in my main class. Change the wsdlLocation to point to a file in my source code (instead of a URL)
@WebServiceClient(name = "Service1", targetNamespace = "https://example.org/", wsdlLocation = "WebService.wsdl")
public class Service1
...
Modified WebService.wsdl file:
<wsp:Policy wsu:Id="BasicHttpBinding_IService1_policy">
<wsp:ExactlyOne/>
</wsp:Policy>