We need to implement the following Interceptor
@Component
public class CustomEndpointInterceptor extends EndpointInterceptorAdapter {
private static final Log LOG = LogFactory.getLog(CustomEndpointInterceptor.class);
private static final String SOAP_ENV_NAMESPACE = "http://schemas.xmlsoap.org/soap/envelope/";
private static final String PREFERRED_PREFIX = "infasoapns";
@Override
public boolean handleResponse(MessageContext messageContext, Object endpoint) throws Exception {
LOG.info("Endpoint Response Handling");
SaajSoapMessage soapResponse = (SaajSoapMessage) messageContext.getResponse();
alterSoapEnvelope(soapResponse);
return super.handleResponse(messageContext, endpoint);
}
@Override
public boolean handleFault(MessageContext messageContext, Object endpoint) throws Exception {
LOG.info("Endpoint Response Handling");
SaajSoapMessage soapResponse = (SaajSoapMessage) messageContext.getResponse();
alterSoapEnvelope(soapResponse);
return super.handleFault(messageContext, endpoint);
}
private void alterSoapEnvelope(SaajSoapMessage soapResponse) {
try {
SOAPMessage soapMessage = soapResponse.getSaajMessage();
SOAPPart soapPart = soapMessage.getSOAPPart();
SOAPEnvelope envelope = soapPart.getEnvelope();
SOAPHeader header = soapMessage.getSOAPHeader();
SOAPBody body = soapMessage.getSOAPBody();
SOAPFault fault = body.getFault();
envelope.removeNamespaceDeclaration(envelope.getPrefix());
envelope.addNamespaceDeclaration(PREFERRED_PREFIX, SOAP_ENV_NAMESPACE);
envelope.setPrefix(PREFERRED_PREFIX);
header.setPrefix(PREFERRED_PREFIX);
body.setPrefix(PREFERRED_PREFIX);
addDesiredBodyNamespaceEntries(body.getChildElements());
removeUndesiredBodyNamespaceEntries(body.getChildElements());
if (fault != null) {
fault.setPrefix(PREFERRED_PREFIX);
}
} catch (SOAPException e) {
e.printStackTrace();
}
}
private void addDesiredBodyNamespaceEntries(Iterator childElements) {
while (childElements.hasNext()) {
final Object childElementNode = childElements.next();
if (childElementNode instanceof SOAPElement) {
SOAPElement soapElement = (SOAPElement) childElementNode;
// set desired namespace body element prefix
soapElement.setPrefix("tns");
// recursively set desired namespace prefix entries in child elements
addDesiredBodyNamespaceEntries(soapElement.getChildElements());
}
}
}
private void removeUndesiredBodyNamespaceEntries(Iterator childElements) {
while (childElements.hasNext()) {
final Object childElementNode = childElements.next();
if (childElementNode instanceof SOAPElement) {
SOAPElement soapElement = (SOAPElement) childElementNode;
// we remove any prefix/namespace entries added by JAX-WS in the body element that is not the one we want
for (String prefix : getNamespacePrefixList(soapElement.getNamespacePrefixes())) {
if (prefix != null && ! "tns".equals(prefix)) {
soapElement.removeNamespaceDeclaration(prefix);
}
}
// recursively remove prefix/namespace entries in child elements
removeUndesiredBodyNamespaceEntries(soapElement.getChildElements());
}
}
}
private Set<String> getNamespacePrefixList(Iterator namespacePrefixIter) {
Set<String> namespacePrefixesSet = new HashSet<>();
while (namespacePrefixIter.hasNext()) {
namespacePrefixesSet.add((String) namespacePrefixIter.next());
}
return namespacePrefixesSet;
}
}
and add the following code segment to the Webservice config
@Override
public void addInterceptors(List<EndpointInterceptor> interceptors) {
// register global interceptor
interceptors.add(new CustomEndpointInterceptor());
// register endpoint specific interceptor
interceptors.add(new PayloadRootSmartSoapEndpointInterceptor(
new CustomEndpointInterceptor(),
ValidationEndpoint.NAMESPACE_URI,
ValidationEndpoint.LOCAL_PART));
}