SOAP webservice endpoint from WSDL

11,489

Getting a 405 (Method not Allowed) error code when accessing a SOAP service with a browser (i.e. via a GET) is actually correct behavior: all SOAP HTTP access is done via a POST, not a GET.

You can try pointing a SOAP client at the WSDL ( SoapUI for example), and see if that works instead.

Share:
11,489

Related videos on Youtube

S chakraborty
Author by

S chakraborty

Updated on June 04, 2022

Comments

  • S chakraborty
    S chakraborty almost 2 years

    I am new to the SOAP web service and so referenced one of the tutorial to create a SOAP webservice using Spring. . I have created the wsdl from the xsd that looks like this.

    <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://spring.io/guides/gs-producing-web-service"
               targetNamespace="http://spring.io/guides/gs-producing-web-service" elementFormDefault="qualified">
    
        <xs:element name="getCountryRequest">
            <xs:complexType>
                <xs:sequence>
                    <xs:element name="name" type="xs:string"/>
                </xs:sequence>
            </xs:complexType>
        </xs:element>
    
        <xs:element name="getCountryResponse">
            <xs:complexType>
                <xs:sequence>
                    <xs:element name="country" type="tns:country"/>
                </xs:sequence>
            </xs:complexType>
        </xs:element>
    
        <xs:complexType name="country">
            <xs:sequence>
                <xs:element name="name" type="xs:string"/>
                <xs:element name="population" type="xs:int"/>
                <xs:element name="capital" type="xs:string"/>
                <xs:element name="currency" type="tns:currency"/>
            </xs:sequence>
        </xs:complexType>
    
        <xs:simpleType name="currency">
            <xs:restriction base="xs:string">
                <xs:enumeration value="GBP"/>
                <xs:enumeration value="EUR"/>
                <xs:enumeration value="PLN"/>
            </xs:restriction>
        </xs:simpleType>
    </xs:schema>
    

    I have also created the service endpoint below.

    package hello;
    
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.ws.server.endpoint.annotation.Endpoint;
    import org.springframework.ws.server.endpoint.annotation.PayloadRoot;
    import org.springframework.ws.server.endpoint.annotation.RequestPayload;
    import org.springframework.ws.server.endpoint.annotation.ResponsePayload;
    
    import io.spring.guides.gs_producing_web_service.GetCountryRequest;
    import io.spring.guides.gs_producing_web_service.GetCountryResponse;
    
    @Endpoint
    public class CountryEndpoint {
        private static final String NAMESPACE_URI = "http://spring.io/guides/gs-producing-web-service";
    
        private CountryRepository countryRepository;
    
        @Autowired
        public CountryEndpoint(CountryRepository countryRepository) {
            this.countryRepository = countryRepository;
        }
    
        @PayloadRoot(namespace = NAMESPACE_URI, localPart = "getCountryRequest")
        @ResponsePayload
        public GetCountryResponse getCountry(
                @RequestPayload GetCountryRequest request) {
            GetCountryResponse response = new GetCountryResponse();
            response.setCountry(countryRepository.findCountry(request.getName()));
    
            return response;
        }
    }
    

    And configured the bean like this.

    package hello;
    
    import org.springframework.boot.context.embedded.ServletRegistrationBean;
    import org.springframework.context.ApplicationContext;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.core.io.ClassPathResource;
    import org.springframework.ws.config.annotation.EnableWs;
    import org.springframework.ws.config.annotation.WsConfigurerAdapter;
    import org.springframework.ws.transport.http.MessageDispatcherServlet;
    import org.springframework.ws.wsdl.wsdl11.DefaultWsdl11Definition;
    import org.springframework.xml.xsd.SimpleXsdSchema;
    import org.springframework.xml.xsd.XsdSchema;
    
    @EnableWs
    @Configuration
    public class WebServiceConfig extends WsConfigurerAdapter {
        @Bean
        public ServletRegistrationBean dispatcherServlet(ApplicationContext applicationContext) {
            MessageDispatcherServlet servlet = new MessageDispatcherServlet();
            servlet.setApplicationContext(applicationContext);
            servlet.setTransformWsdlLocations(true);
            return new ServletRegistrationBean(servlet, "/ws/*");
        }
    
        @Bean(name = "countries")
        public DefaultWsdl11Definition defaultWsdl11Definition(XsdSchema countriesSchema) {
            DefaultWsdl11Definition wsdl11Definition = new DefaultWsdl11Definition();
            wsdl11Definition.setPortTypeName("CountriesPort");
            wsdl11Definition.setLocationUri("http://localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/");
            wsdl11Definition.setTargetNamespace("http://spring.io/guides/gs-producing-web-service");
            wsdl11Definition.setSchema(countriesSchema);
            return wsdl11Definition;
        }
    
        @Bean
        public XsdSchema countriesSchema() {
            return new SimpleXsdSchema(new ClassPathResource("countries.xsd"));
        }
    }
    

    After deploying the WAR file into tomcat server i am able to see the WSDL at http://localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/countries.wsdl which looks like this.

    <wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:sch="http://spring.io/guides/gs-producing-web-service" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:tns="http://spring.io/guides/gs-producing-web-service" targetNamespace="http://spring.io/guides/gs-producing-web-service">
    <wsdl:types>
    <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" targetNamespace="http://spring.io/guides/gs-producing-web-service">
    <xs:element name="getCountryRequest">
    <xs:complexType>
    <xs:sequence>
    <xs:element name="name" type="xs:string"/>
    </xs:sequence>
    </xs:complexType>
    </xs:element>
    <xs:element name="getCountryResponse">
    <xs:complexType>
    <xs:sequence>
    <xs:element name="country" type="tns:country"/>
    </xs:sequence>
    </xs:complexType>
    </xs:element>
    <xs:complexType name="country">
    <xs:sequence>
    <xs:element name="name" type="xs:string"/>
    <xs:element name="population" type="xs:int"/>
    <xs:element name="capital" type="xs:string"/>
    <xs:element name="currency" type="tns:currency"/>
    </xs:sequence>
    </xs:complexType>
    <xs:simpleType name="currency">
    <xs:restriction base="xs:string">
    <xs:enumeration value="GBP"/>
    <xs:enumeration value="EUR"/>
    <xs:enumeration value="PLN"/>
    </xs:restriction>
    </xs:simpleType>
    </xs:schema>
    </wsdl:types>
    <wsdl:message name="getCountryRequest">
    <wsdl:part element="tns:getCountryRequest" name="getCountryRequest"></wsdl:part>
    </wsdl:message>
    <wsdl:message name="getCountryResponse">
    <wsdl:part element="tns:getCountryResponse" name="getCountryResponse"></wsdl:part>
    </wsdl:message>
    <wsdl:portType name="CountriesPort">
    <wsdl:operation name="getCountry">
    <wsdl:input message="tns:getCountryRequest" name="getCountryRequest"></wsdl:input>
    <wsdl:output message="tns:getCountryResponse" name="getCountryResponse"></wsdl:output>
    </wsdl:operation>
    </wsdl:portType>
    <wsdl:binding name="CountriesPortSoap11" type="tns:CountriesPort">
    <soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/>
    <wsdl:operation name="getCountry">
    <soap:operation soapAction=""/>
    <wsdl:input name="getCountryRequest">
    <soap:body use="literal"/>
    </wsdl:input>
    <wsdl:output name="getCountryResponse">
    <soap:body use="literal"/>
    </wsdl:output>
    </wsdl:operation>
    </wsdl:binding>
    <wsdl:service name="CountriesPortService">
    <wsdl:port binding="tns:CountriesPortSoap11" name="CountriesPortSoap11">
    <soap:address location="`http://localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/`"/>
    </wsdl:port>
    </wsdl:service>
    </wsdl:definitions>
    

    I am able to see the WSDLon the server but unable to find the service endpoint to send the SOAP request. I refereed several tutorials but was unable to figure out the endpoint. Hitting at http://localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/ returns a 405 error. Please help me out on this.

    • morgano
      morgano over 9 years
      This line at almost the end of your wsdl: <soap:address location="`http://localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/`"/‌​> Have you tried without the single quotes? like this: <soap:address location="http://localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/"/>
    • S chakraborty
      S chakraborty over 9 years
      yes, as stack overflow dosen't allow me to mention localhost:8080 I have highlighted the same. My actual wsdl has <soap:address location="localhost:8080/Demo2-0.0.1-SNAPSHOT/ws/">. Sorry for the inconvinience.
  • talegna
    talegna about 9 years
    I don't think you are wrong but remember link only answers, although they may answer the question, can become irrelevant with time; See this article about how to answer: "Links to external resources are encouraged, but please add context around the link so your fellow users will have some idea what it is and why it’s there. Always quote the most relevant part of an important link, in case the target site is unreachable or goes permanently offline."