Re: Collecting issues against WSDL 1.1

ryman@ca.ibm.com wrote:

> Jean-Jacques,
>
> Pls add this issues to the list:(See attached file: wsdl11-issues.zip)Thx.
> See you in San Jose.
>
> Arthur Ryman, PhD
> Senior Technical Staff Member
> WebSphere Studio Advanced Development and Web Services Tools Architect
>
> phone: 905-413-3077, TL 969-3077
> assistant: 905-413-2323, TL 969-2323
> fax: 905-413-4920, TL 969-4920
> intranet: http://w3.torolab.ibm.com/~ryman/
>
>   -----------------------------------------------------------------
>                         Name: wsdl11-issues.zip
>    wsdl11-issues.zip    Type: Zip Compressed Data (application/x-zip-compressed)
>                     Encoding: base64

[WSDL 1.1 Issues.html converted to plain text.]

WSDL 1.1 Issues

Arthur Ryman
2002-04-07

Introduction

This document describes some issues with WSDL 1.1 that were encountered
during the development of Web services tools at IBM. The main issues
encountered are:

  1. The binding extensions depend on the structure of the portType.
  2. The binding extension for SOAP is defined in terms of features that
     interact in a complex way.
  3. The binding extension for SOAP cannot describe SOAP messages that mix
     encoding styles at the message part level.
  4. The binding extension for HTTP GET or POST does not cover the case of
     attributes in a complex input type.

These issues are described in more detail below.

Binding Extensions Depend on the Structure of the portType

The portType is supposed to represent the abstract interface of a service
without reference to how the service is accessed. However, the current
design couples the binding extensions with the structure of the portType
making it necessary to define a separate portType for each binding
extension. SOAP RPC Style, SOAP Document Style, and HTTP GET or PORT each
require specific structure in the portType, yet all can be used to access
the same logical service.

It is useful to provide HTTP GET and POST endpoints for a service in
addition to a SOAP/HTTP endpoint. Each endpoint should provide access to
the same underlying service. It is therefore reasonable to expect that each
endpoint should be bound to the same portType. The portType should be an
abstract definition of the interface of the service. The bindings should
describe how to access the service using a given protocol. However, the
binding extensions for HTTP GET and POST are not defined in a way that
allows them to use the same portType as SOAP/HTTP. To work around this
problem, an additional, but semantically equivalent portType, must be
defined.

To illustrate this problem, consider a stock quote service that has a
single operation, getQuote, that takes a string symbol as input and returns
a float price as output. Consider the WSDL for this service as created
using:

   * IBM WebSphere Studio: IBMStockQuoteService.wsdl
   * Microsoft Visual Studio .NET: MSStockQuoteService.wsdl

WSDL 1.1 defines messages as collections of parts. It is therefore natural
to define the input message as having a single part named symbol of type
string, and the output message to have a single part named price or return
of type float. With this definition of messages, the SOAP binding is
naturally expressed using the RPC style. Listing 1 shows the SOAP binding
definitions from IBMStockQuoteService.wsdl:

        Listing 1. IBMStockQuoteService.wsdl SOAP RPC Style Binding

   <message name="getQuoteInput">
     <part name="symbol" type="xsd:string"/>
   </message>
   <message name="getQuoteSoapOutput">
     <part name="return" type="xsd:float"/>
   </message>

   <portType name="theSoapPortType">
     <operation name="getQuote">
       <input message="tns:getQuoteInput"/>
       <output message="tns:getQuoteSoapOutput"/>
     </operation>
   </portType>

   <binding name="theSoapBinding" type="tns:theSoapPortType">
     <soap:binding style="rpc"
 transport="http://schemas.xmlsoap.org/soap/http"/>
     <operation name="getQuote">
       <soap:operation
 soapAction="http://tempuri.org/isd/StockQuoteService.isd"/>
       <input>
         <soap:body
           encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"
           namespace="http://tempuri.org/isd/StockQuoteService.isd"
           parts="symbol"
           use="encoded"/>
       </input>
       <output>
         <soap:body
           encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"
           namespace="http://tempuri.org/isd/StockQuoteService.isd"
           parts="return"
           use="encoded"/>
       </output>
     </operation>
   </binding>

However, this portType cannot be used for HTTP GET or POST because the we
want the output to be of MIME type text/xml. Simply returning a float is
not allowed because a float is just an XML fragment, not a valid document.
We therefore need to define a new output message and portType as shown in
Listing 2.

         Listing 2. IBM StockQuote.wsdl HTTP GET and POST Bindings

   <types>
     <schema

 targetNamespace="http://schemas.ibm.com/beans/StockQuoteService.isd/XSD"
       xmlns="http://www.w3.org/2001/XMLSchema"
       xmlns:tns="http://schemas.ibm.com/beans/StockQuoteService.isd/XSD">

       <element name="getQuoteResponse">
         <complexType>
           <sequence>
             <element name="return" type="float"/>
           </sequence>
         </complexType>
       </element>
     </schema>
   </types>

   <message name="getQuoteGetPostOutput">
     <part element="xsd1:getQuoteResponse" name="response"/>
   </message>

   <portType name="theGetPostPortType">
     <operation name="getQuote">
       <wsdl:documentation
 xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">Gets a quote in US dollars
 for a stock symbol.
       </wsdl:documentation>
       <input message="tns:getQuoteInput"/>
       <output message="tns:getQuoteGetPostOutput"/>
     </operation>
   </portType>

   <binding name="theGetBinding" type="tns:theGetPostPortType">
     <http:binding verb="GET"/>
     <operation name="getQuote">
       <http:operation location="getQuote"/>
       <input>
         <http:urlEncoded/>
       </input>
       <output>
         <mime:mimeXml/>
       </output>
     </operation>
   </binding>

   <binding name="thePostBinding" type="tns:theGetPostPortType">
     <http:binding verb="POST"/>
     <operation name="getQuote">
       <http:operation location="getQuote"/>
       <input>
         <mime:content type="application/x-www-form-urlencoded"/>
       </input>
       <output>
         <mime:mimeXml/>
       </output>
     </operation>
   </binding>

In Listing 2, getQuoteReponse has a root element that includes all the
output message parts as children. This style of response accommodates any
number of output message parts (zero, one, or more than one). Listing 3
shows a typical response using the getQuoteResponse element (see
IBMgetQuoteResponse.xml).

       Listing 3. IBMStockQuoteService.wsdl HTTP GET or POST Response

 <?xml version="1.0"?>
 <xsd1:getQuoteResponse
   xmlns:xsd1="http://schemas.ibm.com/beans/StockQuoteService.isd/XSD"
   xmlns:xsd="http://www.w3.org/2001/XMLSchema"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
   <return xsi:type="xsd:float">100.0</return>
 </xsd1:getQuoteResponse>

The need for a different portType cannot be eliminated by using SOAP
Document style instead of RPC style. Although Document style defines a
suitable output message, the input message is not suitable for URL
encoding. Although in this example, there is just one input message part,
in general there will be more than one part and each part should be bound
as a name=value portion of the query string in URL encoding. Listing 4
shows the SOAP Document style bindings from MSStockService.wsdl.

      Listing 4. MSStockQuoteService.wsdl SOAP Document Style Bindings

   <types>
     <s:schema elementFormDefault="qualified"
 targetNamespace="http://microsoft.com/webservices/">
       <s:element name="getQuote">
         <s:complexType>
           <s:sequence>
             <s:element minOccurs="0" maxOccurs="1" name="symbol"
 type="s:string" />
           </s:sequence>
         </s:complexType>
       </s:element>
       <s:element name="getQuoteResponse">
         <s:complexType>
           <s:sequence>
             <s:element minOccurs="1" maxOccurs="1" name="getQuoteResult"
 type="s:float" />
           </s:sequence>
         </s:complexType>
       </s:element>
     </s:schema>
   </types>

   <message name="getQuoteSoapIn">
     <part name="parameters" element="s0:getQuote" />
   </message>
   <message name="getQuoteSoapOut">
     <part name="parameters" element="s0:getQuoteResponse" />
   </message>

   <portType name="StockQuoteServiceSoap">
     <operation name="getQuote">
       <input message="s0:getQuoteSoapIn" />
       <output message="s0:getQuoteSoapOut" />
     </operation>
   </portType>

   <binding name="StockQuoteServiceSoap" type="s0:StockQuoteServiceSoap">
     <soap:binding transport="http://schemas.xmlsoap.org/soap/http"
 style="document" />
     <operation name="getQuote">
       <soap:operation
 soapAction="http://microsoft.com/webservices/getQuote" style="document"
 />
       <input>
         <soap:body use="literal" />
       </input>
       <output>
         <soap:body use="literal" />
       </output>
     </operation>
   </binding>

Note that the messages for the SOAP Document style binding are different
than those for the SOAP RPC style binding even though they both describe
the same service. Listing 5 shows the HTTP GET and POST bindings.

       Listing 5. MSStockQuoteService.wsdl HTTP GET and POST Bindings

   <types>
     <s:schema elementFormDefault="qualified"
 targetNamespace="http://microsoft.com/webservices/">
       <s:element name="float" type="s:float" />
     </s:schema>
   </types>

   <message name="getQuoteHttpGetIn">
     <part name="symbol" type="s:string" />
   </message>
   <message name="getQuoteHttpGetOut">
     <part name="Body" element="s0:float" />
   </message>

   <message name="getQuoteHttpPostIn">
     <part name="symbol" type="s:string" />
   </message>
   <message name="getQuoteHttpPostOut">
     <part name="Body" element="s0:float" />
   </message>

   <portType name="StockQuoteServiceHttpGet">
     <operation name="getQuote">
       <input message="s0:getQuoteHttpGetIn" />
       <output message="s0:getQuoteHttpGetOut" />
     </operation>
   </portType>

   <portType name="StockQuoteServiceHttpPost">
     <operation name="getQuote">
       <input message="s0:getQuoteHttpPostIn" />
       <output message="s0:getQuoteHttpPostOut" />
     </operation>
   </portType>

   <binding name="StockQuoteServiceHttpGet"
 type="s0:StockQuoteServiceHttpGet">
     <http:binding verb="GET" />
     <operation name="getQuote">
       <http:operation location="/getQuote" />
       <input>
         <http:urlEncoded />
       </input>
       <output>
         <mime:mimeXml part="Body" />
       </output>
     </operation>
   </binding>

   <binding name="StockQuoteServiceHttpPost"
 type="s0:StockQuoteServiceHttpPost">
     <http:binding verb="POST" />
     <operation name="getQuote">
       <http:operation location="/getQuote" />
       <input>
         <mime:content type="application/x-www-form-urlencoded" />
       </input>
       <output>
         <mime:mimeXml part="Body" />
       </output>
     </operation>
   </binding>

Here an element named float is defined to wrap the float result. This style
assumes there is a single output message part. Note that although two
portTypes are defined here, they are the same. Listing 6 shows a typical
response using the float element (see MSgetQuoteResponse.xml).

       Listing 6. MSStockQuoteService.wsdl HTTP GET or POST Response

 <?xml version="1.0" encoding="utf-8"?>
 <float xmlns="http://microsoft.com/webservices/">100</float>

As can be seen from these examples, the portType is strongly coupled to the
binding extension which prevents portTypes from being reused across
different binding extensions.

Potential Solutions

   * Expand the definitions of the binding extensions so they can be
     applied to any portType. For example, in the HTTP GET or POST
     bindings, define how the response is generated from a message that has
     several parts.
   * Eliminate message definitions and instead define portTypes directly in
     terms of XML Schema types. Use XPath to bind parts of the schema to
     the protocol.

The binding extension for SOAP is defined in terms of features that
interact in a complex way

The binding extension for SOAP depends on the following features:

   * The message part XSD style, either type or element.
   * The SOAP style, either RPC or Document.
   * The encoding style, either literal or encoded.
   * The direction of the message, either input or output.

Since each of these four properties has two values, there are a total of
sixteen possible combinations. The text of the WSDL 1.1 specification
should be clearer about how these properties interact and which
combinations are valid since not all seem to be. Each combination should be
enumerated and described clearly, and illustrated with an example.

It is important to establish the validity and interpretation of each
combination in order to improve interoperability between vendors. For
example, the current version of WebSphere Studio creates services that use
literal encoding in RPC style, but the current version of Microsoft Visual
Studio .NET does not support the generation of Web references to that type
of service. It is not clear whether this restriction is based on a belief
that the combination is not valid, or is simply a prioritization of
function delivery.

The binding extension for SOAP cannot describe SOAP messages that mix
encoding styles at the message part level

The SOAP 1.1 specification allows an encodingStyle attribute to be used on
any element of a SOAP message (see 4.1.1 SOAP encodingStyle Attribute). For
example, each part of a message could be encoded using a different style.
In practice, some parts might be SOAP encoded while others are literal.
However, in WSDL 1.1, encoding can only be specified at the message level.
Therefore WSDL 1.1 cannot accurately describe services that use more than
one encoding styles in a single message.

The binding extension for HTTP GET or POST does not cover the case of
attributes in a complex input type

In WSDL 1.1 it is possible to defined an input message part that is a
complex XML schema type. For example, Listing 7 shows Person.xsd which
defines the complex type PersonType.
                           Listing 7. Person.xsd

 <?xml version="1.0" encoding="UTF-8"?>
 <schema xmlns="http://www.w3.org/2001/XMLSchema"
 targetNamespace="http://www.ibm.com" xmlns:Person="http://www.ibm.com">

     <complexType name="PersonType">
         <sequence>
             <element name="name" type="string"></element>
             <element name="birthdate" type="date"></element>
         </sequence>
     </complexType>
 </schema>

The WSDL 1.1 specification does not explicitly describe how to URL encode
complex types, but a reasonable interpretation is to use the serialized
content as a the query string value. For example, suppose an input message
has a part named employee of type PersonType. This part would be passed in
a query string as:

employee=<name>John Doe</name><birthdate>1960-01-01</birthdate>

Now suppose that PersonType had an attribute named sex as defined in
PersonAttr.xsd which is shown in Listing 8.

                         Listing 8. PersonAttr.xsd

 <?xml version="1.0" encoding="UTF-8"?>
 <schema xmlns="http://www.w3.org/2001/XMLSchema"
 targetNamespace="http://www.ibm.com" xmlns:Person="http://www.ibm.com">

     <complexType name="PersonType">
         <sequence>
             <element name="name" type="string"></element>
             <element name="birthdate" type="date"></element>
         </sequence>
         <attribute name="sex" type="string"></attribute>
     </complexType>
 </schema>

How would this be passed in a query string? Clearly the WSDL 1.1 is silent
on this topic. The WSDL 1.1 specification should either explicitly disallow
attributes, or should define some serialization that can be used with URL
encoding, e.g. prefix the content with a comma-separated list of attribute
values enclosed in square brackets:

employee=[sex(male)]<name>John Doe</name><birthdate>1960-01-01</birthdate>

Conclusion

The above issues indicate that perhaps the notion of message parts is not
flexible enough to achieve the goal of defining portTypes that can be used
in different binding extensions. A way out of this problem might be to
directly use XML Schema to define the input and output messages of a
service and to interpret these schemas as abstract. Certainly XML Schema is
expressive enough as a data definition language. Using XML Schema would
eliminate any binding-oriented bias that the use of message parts
introduces.

The problem of defining message parts is then shifted to the binding
extension. In the case of SOAP Document binding, the abstract XML Schema
definitions can be regarded as concrete. In the case of SOAP RPC, message
parts could be defined using XPath expressions. A limited subset of XPath
should be adequate for this purpose. Similarly, for HTTP GET and POST, the
inputs could be defined using XPath and the output can directly use the XML
Schema.

Received on Tuesday, 9 April 2002 03:54:53 UTC