Can't get Spring SOAP Client to work: content type 'text/xml; charset=utf-8' was not the expected type 'application/soap+xml; charset=utf-8'
Asked Answered
R

4

6

Hi, I am trying to make a simple soap client work using Spring-ws. The googling I've done on this error says I'm using Soap 1.1 and need to specify Soap 1.2. I've tried to do that. Am I doing it correctly below? If this is not the problem does anybody see what the problem is?

Here's a chunk of the stack trace:

org.springframework.ws.client.WebServiceTransportException: Cannot process the message because the content type 'text/xml; charset=utf-8' was not the expected type 'application/soap+xml; charset=utf-8'. [415]
    at org.springframework.ws.client.core.WebServiceTemplate.handleError(WebServiceTemplate.java:663)
    at org.springframework.ws.client.core.WebServiceTemplate.doSendAndReceive(WebServiceTemplate.java:587)
    at org.springframework.ws.client.core.WebServiceTemplate.sendAndReceive(WebServiceTemplate.java:537)
    at org.springframework.ws.client.core.WebServiceTemplate.doSendAndReceive(WebServiceTemplate.java:492)
    at org.springframework.ws.client.core.WebServiceTemplate.sendSourceAndReceiveToResult(WebServiceTemplate.java:436)
    at com.jda.fileserver.FujiAuthenticationTest.testLogin(FujiAuthenticationTest.java:53)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)

Here's my code, thanks for trying to help:

public class AuthTest {
@Test
public void testLogin() throws Exception {
        StringBuffer loginXml = new StringBuffer();
        loginXml.append("<soapenv:Envelope xmlns:soapenv=\"http://www.w3.org/2003/05/soap-envelope\" xmlns:ns=\"http://abc.com/xyz/2010/08\">");
        loginXml.append("  <soapenv:Header>");
        loginXml.append("    <ns:loginOperationDetails>");
        loginXml.append("    </ns:loginOperationDetails>");
        loginXml.append("  </soapenv:Header>");
        loginXml.append("  <soapenv:Body>");
        loginXml.append("    <ns:LogIn>");
        loginXml.append("      <ns:logInInfo>");
        loginXml.append("        <ns:CustomerAccountId>customer1</ns:CustomerAccountId>");
        loginXml.append("        <ns:Username>jsmith</ns:Username>");
        loginXml.append("        <ns:Password>abc123</ns:Password>");
        loginXml.append("      </ns:logInInfo>");
        loginXml.append("    </ns:LogIn>");
        loginXml.append("  </soapenv:Body>");
        loginXml.append("</soapenv:Envelope>");

        WebServiceTemplate webServiceTemplate = new WebServiceTemplate();
        SaajSoapMessageFactory defaultMessageFactory = (SaajSoapMessageFactory) webServiceTemplate.getMessageFactory();
        defaultMessageFactory.setSoapVersion(SoapVersion.SOAP_12);
        webServiceTemplate.setMessageFactory(defaultMessageFactory); // probably not needed

        StreamSource source = new StreamSource(new StringReader(loginXml.toString()));
        StreamResult result = new StreamResult(System.out);
        String uri = "http://xyz.abcstage.com/xyz_1.0/membership.svc/ws";
        SoapActionCallback requestCallback = new SoapActionCallback("http://abc.com/xyz/2010/08/MembershipService/LogIn");
        try {
            webServiceTemplate.sendSourceAndReceiveToResult(uri, source, requestCallback, result);
        } 
        catch (SoapFaultException sfe) {
            throw new Exception("SoapFaultException", sfe);
        }
        catch (WebServiceTransportException wste) {
            throw new Exception("WebServiceTransportException", wste);
        }
    }
}
Rockingham answered 27/1, 2013 at 15:9 Comment(2)
Did you get the error as well when you didn't try and set the SoapVersion on the MessageFactory?Rotate
Yes. Also I just hooked up wireshark and my client is definitely sending content-type: text/xml instead of application/soap+xml.Rockingham
R
4

Ok, I fixed the above problem, which gets me to another problem. First here's how I fixed the above problem. Now I don't set the SOAP version on the SaajSoapMessageFactory, I set it on the wrapped MessageFactory. Now the Content-Type going out in my request is application/soap+xml.

WebServiceTemplate webServiceTemplate = new WebServiceTemplate();
MessageFactory msgFactory = MessageFactory.newInstance(SOAPConstants.SOAP_1_2_PROTOCOL);
SaajSoapMessageFactory newSoapMessageFactory = new SaajSoapMessageFactory(msgFactory);
webServiceTemplate.setMessageFactory(newSoapMessageFactory);

Next problem, now I'm getting this:

org.springframework.ws.soap.client.SoapFaultClientException: Unexpected fault in the service.
    at org.springframework.ws.soap.client.core.SoapFaultMessageResolver.resolveFault(SoapFaultMessageResolver.java:37)
    at org.springframework.ws.client.core.WebServiceTemplate.handleFault(WebServiceTemplate.java:774)
    at org.springframework.ws.client.core.WebServiceTemplate.doSendAndReceive(WebServiceTemplate.java:600)
    at org.springframework.ws.client.core.WebServiceTemplate.sendAndReceive(WebServiceTemplate.java:537)
    at org.springframework.ws.client.core.WebServiceTemplate.doSendAndReceive(WebServiceTemplate.java:492)
    at org.springframework.ws.client.core.WebServiceTemplate.sendSourceAndReceiveToResult(WebServiceTemplate.java:436)

and here's the info that was returned in the response:

500 Internal Server Error
The SOAP action specified on the message, '', does not match the HTTP SOAP Action, 'http://abc.com/xyz/2010/08/MembershipService/LogIn'.

I'll try to solve this, but wanted to update anybody reading this so they can stop looking into the previous error. I need to figure out how to correctly set the soap action.

Rockingham answered 28/1, 2013 at 19:12 Comment(2)
I'm going to close this request and start a fresh one with a title that reflects the current problem.Rockingham
I started a new question here #14571773Rockingham
R
2

Please use the below code to change the header content type to text/xml;charset=utf-8 in Spring webservice template marshallSendAndReceive method.

  WebServiceTemplate webServiceTemplate = new WebServiceTemplate();
webServiceTemplate.marshalSendAndReceive(url, request, new WebServiceMessageCallback() {

                public void doWithMessage(WebServiceMessage message) throws IOException, TransformerException {
                    SaajSoapMessage soapMessage = (SaajSoapMessage) message;
                    MimeHeaders headers = soapMessage.getSaajMessage().getMimeHeaders();
                    headers.addHeader(TransportConstants.HEADER_CONTENT_TYPE, "text/xml;charset=utf-8");
Robotize answered 7/12, 2018 at 9:56 Comment(1)
Thank you Abhishek. Unfortunately I no longer work on that project, for that company, or in the field of software development any more. I enjoyed reading your answer though.Rockingham
G
0

For adding soapheader with action and to tags, below code is working fine for me.

public void doWithMessage(WebServiceMessage message) throws IOException {
    SaajSoapMessage soapMessage = (SaajSoapMessage) message;

    SoapEnvelope soapEnvelope = soapMessage.getEnvelope();
    SoapHeader soapHeader = soapEnvelope.getHeader();

    //Initialize QName for Action and To
    QName action = new QName("{uri}", "Action", "{actionname}");
    QName to = new QName("{uri}", "To", "{actionname}");

    soapHeader.addNamespaceDeclaration("{actionname}", "{uri}");

    SoapHeaderElement soapHeaderElementAction = soapHeader.addHeaderElement(action);
    SoapHeaderElement soapHeaderElementTo = soapHeader.addHeaderElement(to);

    soapHeaderElementAction.setText("{text inside the tags}");

    soapHeaderElementTo.setText("{text inside the tags}");

    soapMessage.setSoapAction("{add soap action uri}");

    soapMessage.writeTo(out);

}
Guibert answered 28/6, 2019 at 20:53 Comment(0)
W
0

Use setHeader since you want probably want to replace the contents of an existing header or add it if it doesn't exist. Though Httpheaders are supposed to be case insensitive using addHeader with do just that. Debugging through the source code when addHeader() is called even though it ignores case you'll see that it inserts the new header after the other header. So , at least in Java, will end up with

content-type:

Content-Type:

            public void doWithMessage(WebServiceMessage message) throws IOException, TransformerException {
                SaajSoapMessage soapMessage = (SaajSoapMessage) message;
                MimeHeaders headers = soapMessage.getSaajMessage().getMimeHeaders();
                headers.setHeader(TransportConstants.HEADER_CONTENT_TYPE, "text/xml;charset=utf-8");
Wendish answered 26/5, 2021 at 22:19 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.