A beginner's guide to WSDL and an example

I was trying to learn how to consume SOAP services, and I realised that there wasn’t a ton of good content out there.

So I wrote this short guide, which introduces WSDL and includes an example WSDL file that you can use in your own programs.

What is WSDL?

A Web Services Description Language (WSDL) document describes a certain type of web service. Specifically, it describes XML-based web services.

A WSDL file is itself written in XML, and it defines where the web service is located (its endpoint), its operations (methods), the messages exchanged in each operation, and the XML elements, or “data types”, within each message.

A WSDL file typically consists of the following sections:

  • The types element – which defines the data types (XML elements) that are used by the web service. Like “Book” or “Customer”.

  • The message elements – each of which defines a message exchanged with the web service. Perhaps like “GetBook” or “CreateCustomer”

  • portType elements – which combine multiple messages into a single operation – for synchronous operations, this is usually one input and one output.

  • The binding element – which defines exactly how each operation will take place over the network (SOAP, in this example).

  • The service element – which defines where the service is located. Like “http://myservice.com”.

Example WSDL file: BookService.wsdl

So if we want to have a play with WSDL in our programs, we probably need a real example to work with. You can use lots of tools to create a WSDL from scratch, but here’s a shortcut I made.

The example WSDL file below describes a fake web service called BookService which exposes three synchronous (input/output) operations, using SOAP binding:

  • GetBook – to get information about a single book from the collection
  • AddBook – to add a book to the collection
  • GetAllBooks – to retrieve all books from the collection

This example WSDL describes a SOAP service, but WSDL can also be used to describe other types of (non-SOAP) web services too.

Note that although this WSDL has a soap:address, it doesn’t actually point to a real, hosted service.

Feel free to use this WSDL in your own learning. If you end up doing something cool with it, let me know!

<!-- (c) 2015 Tom Donohue. MIT licensed. -->
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<wsdl:definitions xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
                  xmlns:tns="http://www.cleverbuilder.com/BookService/"
                  xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
                  xmlns:xsd="http://www.w3.org/2001/XMLSchema"
                  name="BookService"
                  targetNamespace="http://www.cleverbuilder.com/BookService/">
  <wsdl:documentation>Definition for a web service called BookService,
    which can be used to add or retrieve books from a collection.
  </wsdl:documentation>

  <!--
      The `types` element defines the data types (XML elements)
      that are used by the web service.
   -->
  <wsdl:types>
    <xsd:schema targetNamespace="http://www.cleverbuilder.com/BookService/">
      <xsd:element name="Book">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element name="ID" type="xsd:string" minOccurs="0"/>
            <xsd:element name="Title" type="xsd:string"/>
            <xsd:element name="Author" type="xsd:string"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
      <xsd:element name="Books">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element ref="tns:Book" minOccurs="0" maxOccurs="unbounded"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>

      <xsd:element name="GetBook">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element name="ID" type="xsd:string"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
      <xsd:element name="GetBookResponse">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element ref="tns:Book" minOccurs="0" maxOccurs="1"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>

      <xsd:element name="AddBook">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element ref="tns:Book" minOccurs="1" maxOccurs="1"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
      <xsd:element name="AddBookResponse">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element ref="tns:Book" minOccurs="0" maxOccurs="1"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
      <xsd:element name="GetAllBooks">
        <xsd:complexType/>
      </xsd:element>
      <xsd:element name="GetAllBooksResponse">
        <xsd:complexType>
          <xsd:sequence>
            <xsd:element ref="tns:Book" minOccurs="0" maxOccurs="unbounded"/>
          </xsd:sequence>
        </xsd:complexType>
      </xsd:element>
    </xsd:schema>
  </wsdl:types>


  <!--
      A wsdl `message` element is used to define a message
      exchanged between a web service, consisting of zero
      or more `part`s.
   -->

  <wsdl:message name="GetBookRequest">
    <wsdl:part element="tns:GetBook" name="parameters"/>
  </wsdl:message>
  <wsdl:message name="GetBookResponse">
    <wsdl:part element="tns:GetBookResponse" name="parameters"/>
  </wsdl:message>
  <wsdl:message name="AddBookRequest">
    <wsdl:part name="parameters" element="tns:AddBook"></wsdl:part>
  </wsdl:message>
  <wsdl:message name="AddBookResponse">
    <wsdl:part name="parameters" element="tns:AddBookResponse"></wsdl:part>
  </wsdl:message>
  <wsdl:message name="GetAllBooksRequest">
    <wsdl:part name="parameters" element="tns:GetAllBooks"></wsdl:part>
  </wsdl:message>
  <wsdl:message name="GetAllBooksResponse">
    <wsdl:part name="parameters" element="tns:GetAllBooksResponse"></wsdl:part>
  </wsdl:message>

  <!--
      A WSDL `portType` is used to combine multiple `message`s
      (e.g. input, output) into a single operation.

      Here we define three synchronous (input/output) operations
      and the `message`s that must be used for each.
   -->
  <wsdl:portType name="BookService">
    <wsdl:operation name="GetBook">
      <wsdl:input message="tns:GetBookRequest"/>
      <wsdl:output message="tns:GetBookResponse"/>
    </wsdl:operation>
    <wsdl:operation name="AddBook">
      <wsdl:input message="tns:AddBookRequest"></wsdl:input>
      <wsdl:output message="tns:AddBookResponse"></wsdl:output>
    </wsdl:operation>
    <wsdl:operation name="GetAllBooks">
      <wsdl:input message="tns:GetAllBooksRequest"></wsdl:input>
      <wsdl:output message="tns:GetAllBooksResponse"></wsdl:output>
    </wsdl:operation>
  </wsdl:portType>

  <!--
      The `binding` element defines exactly how each
      `operation` will take place over the network.
      In this case, we are using SOAP.
   -->
  <wsdl:binding name="BookServiceSOAP" type="tns:BookService">
    <soap:binding style="document"
                  transport="http://schemas.xmlsoap.org/soap/http"/>
    <wsdl:operation name="GetBook">
      <soap:operation
              soapAction="http://www.cleverbuilder.com/BookService/GetBook"/>
      <wsdl:input>
        <soap:body use="literal"/>
      </wsdl:input>
      <wsdl:output>
        <soap:body use="literal"/>
      </wsdl:output>
    </wsdl:operation>
    <wsdl:operation name="AddBook">
      <soap:operation
              soapAction="http://www.cleverbuilder.com/BookService/AddBook"/>
      <wsdl:input>
        <soap:body use="literal"/>
      </wsdl:input>
      <wsdl:output>
        <soap:body use="literal"/>
      </wsdl:output>
    </wsdl:operation>
    <wsdl:operation name="GetAllBooks">
      <soap:operation
              soapAction="http://www.cleverbuilder.com/BookService/GetAllBooks"/>
      <wsdl:input>
        <soap:body use="literal"/>
      </wsdl:input>
      <wsdl:output>
        <soap:body use="literal"/>
      </wsdl:output>
    </wsdl:operation>
  </wsdl:binding>

  <!--
      The `service` element finally says where the service
      can be accessed from - in other words, its endpoint.
   -->
  <wsdl:service name="BookService">
    <wsdl:port binding="tns:BookServiceSOAP" name="BookServiceSOAP">
      <soap:address location="http://www.example.org/BookService"/>
    </wsdl:port>
  </wsdl:service>
</wsdl:definitions>

If you want to see this WSDL used in an Apache Camel application, then you can see the file here:

See this example in a Camel app on GitHub