CSE134A LECTURE NOTES

November 20, 2002
 
 

ANNOUNCEMENTS

CAPE will be coming next Monday, November 25.  There will be no lecture on Wednesday November 27, because of Thanksgiving the next day.

The lecture on Wednesday December 4 will be a review session conducted by the TAs.  The final exam will be on Monday December 9, from 7pm to 10pm, in the lecture room (Center Hall 109).

See Discus for important suggestions about the current project.
 
 

WEB SERVICES

There are two views of the theme of this course.  The more pedestrian and technical view is server-side programming for the web.  The more ambitious view is "web services."

Today we'll look at SOAP, a simple but useful standard for building web services.  SOAP was defined in 1999, but the definition is still evolving and it is not an official, stable standard yet.  We'll discuss a subset of SOAP 1.1.  There are many implementations of it available, but very few public services using it--we'll discuss possible reasons later.
 
 

SIMPLE OBJECT ACCESS PROTOCOL (SOAP)

SOAP is a protocol for doing remote procedure calls (RPC).  SOAP uses XML to represent arguments and also results.  The message from the client and the response from the server are transmitted using the POST commands in the HTTP protocol.

SOAP is built on top of HTTP because HTTP traffic is permitted by most firewalls.  Note the paradox: because firewalls view other protocols as security risks, we are punching security holes into HTTP.  However, security software can look at SOAP messages in HTTP and decide whether or not to accept them based on the the identity of the client and the server, and the name of the method being called.  SOAP calls and responses can be encrypted using SSL, like web pages.

Despite its name, SOAP does not assume object-orientedness.  For this reason it is easy to use for small and simple servers, like sensor devices, and server languages, like PHP.
 
 

IMPLEMENTING SOAP IN PHP

To implement a SOAP client, all you need to do is use the socket functions of PHP to send the appropriate HTTP post commands to the SOAP server.

To implement a SOAP server, you need to write a PHP script with the right name so that when a client sends a POST request to your web server, this script is executed.  The server script must then look at the POST commands sent by the client to figure out what the client wants.

If the client sends a Content-Type that the PHP runtime does not recognize, then the POST data received from the client will be available to your script in the variable $HTTP_RAW_POST_DATA.   Your script can then parse the XML sent by the client, etc.

For this project, you may use the NuSoap library of PHP code, so you do not need to generate or parse POST messages explicitly for SOAP.  However you do need to generate POST messages explicitly to query the USPS server that validates street addresses.  You then need to write screen-scraping code to parse the output of this server.
 
 

AN EXAMPLE OF A SOAP REQUEST

This example of a SOAP request, written by Greg Hamerly, is based on an older version of NuSoap.
POST /soapx4/soap.php HTTP/1.0
User-Agent: SOAPx4 v0.5
Host: dietrich.ganx4.com
Content-Type: text/xml
Content-Length: 559
SOAPAction: "urn:soapinterop"

<?xml version="1.0"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:si="http://soapinterop.org/xsd"
xmlns:ns6="http://soapinterop.org/ilab"
xmlns:ns7="http://soapinterop.org"
SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">
<SOAP-ENV:Body>
    <ns7:echoDate>
        <inputDate>
        </inputDate>
    </ns7:echoDate>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>

The explanation below of this invocation is adapted mainly from A Busy Developer's Guide to SOAP 1.1 by Dave Winer and Jake Savin.  Some explanations here are also taken from http://www.xml.com/pub/a/2000/02/09/feature/ and other web pages.
 
 

ROUTING SOAP REQUESTS

The URI (uniform resource identifier) after POST is to route the request within the server.  A User-Agent and Host must be specified, and the Content-Type is always text/xml.  If Content-Length is specified, it must be correct.

SOAPAction is also used to route the request to a handler on the server.  The application determines how this header element is used.  Microsoft implementations of SOAP place constraints on SOAPAction that make compatibility with other SOAP implementations difficult.

Redundancy allows proxies, firewalls, web servers, etc. to process the call without parsing XML, but also allows the XML payload to be interpreted after the surrounding HTTP message is stripped.
 
 

SOAP PAYLOADS

The payload is a single <SOAP-ENV:Envelope> element containing a single <SOAP-ENV:Body> element, which contains a single element which is the procedure call.  The name of the procedure is the name of this element, whch must be a valid XML element name.

First, note the use of an XML namespace.  Remember that a namespace attribute avoids confusion between names of XML elements defined by different sources, by declaring a prefix for an element and all elements nested inside it.

As procedure parameters, we need to transmit structured data such as arrays.  These are represented in XML elements within the procedure call.  Their names are significant, not their order.  The rules describe an element-normal-form encoding style, in which all values and parts of values of an instance are encoded as child elements, not as attributes.  Types are indicated explicitly using attributes.

Common scalar value types are supported by SOAP 1.1, for example
                  xsd:int      xsd:boolean       xsd:string       xsd:double
and also some less usual ones, for example
          xsd:timeInstant          2001-03-27T00:00:01-08:00
          SOAP-ENC:base64          eW91IGNhbid0IHJlYWQgdGhpcyE=

A parameter value can also be a struct, which is simply an XML element that contains sub-elements.  The names of struct elements are significant, the order of the elements is not.  Here's an example of a four-element array, where each component has a different type:

                 <param SOAP-ENC:arrayType="xsd:ur-type[4]" xsi:type="SOAP-ENC:Array">
                <item xsi:type="xsd:int">12</item>
                <item xsi:type="xsd:string">Egypt</item>
                <item xsi:type="xsd:boolean">0</item>
                <item xsi:type="xsd:int">-31</item>
          </param>

If the array elements are of a single type, the value of the array element's SOAP-ENC:arrayType specifies the type of the array's sub-elements, for example, SOAP-ENC:arrayType="xsd:int[4]" means an array of four xsd:int elements.  For mixed-type arrays, write SOAP-ENC:arrayType="xsd:ur-type[4]"
 
 

SOAP RESPONSES

After the server-side operation has executed, an HTTP response message will be returned to the client containing the results of the operation.  There are no SOAP-specific HTTP response headers.  However, the HTTP payload will contain an XML document that contains the results of the operation.

Upon receiving the request, the server-side software is expected to execute some code.  How this happens is outside the scope of the SOAP protocol.

Here is an example of a non-error response:

HTTP/1.1 200 OK
Connection: close
Content-Length: 499
Content-Type: text/xml; charset=utf-8
Date: Wed, 28 Mar 2001 05:05:04 GMT
Server: UserLand Frontier/7.0-WinNT

<?xml version="1.0"?>
<SOAP-ENV:Envelope
SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="http://www.w3.org/1999/XMLSchema"
xmlns:xsi="http://www.w3.org/1999/XMLSchema-instance">

<SOAP-ENV:Body>
      <m:getStateNameResponse xmlns:m="http://www.soapware.org/">
          <Result xsi:type="xsd:string">South Dakota</Result>
      </m:getStateNameResponse>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>

Unless there's an error, return 200 OK.  The body of the response is a single <SOAP-ENV:Envelope> element with one <SOAP-ENV:Body> element, which contains a single element with a name which must match the name of the procedure that was called, with the word "Response" appended.  The actual value of the response is contained in the single optional sub-element of the wrapper, which must be like a valid parameter.  If the wrapper has no sub-elements then the procedure did not return a value.
 
 

ERROR RESPONSES

Alternatively, here is an example of an error response:
HTTP/1.1 500 Internal Server Error
Date: Mon, 19 Nov 2001 06:03:35 GMT
Server: Apache/1.3.20 (Unix) PHP/4.0.6 mod_gzip/1.3.19.1a
X-Powered-By: PHP/4.0.6
Connection: Close
Content-Length: 795
Content-Type: text/xml; charset=UTF-8

<?xml version="1.0"?>
<SOAP-ENV:Envelope
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:si="http://soapinterop.org/xsd"  SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">

<SOAP-ENV:Body>
    <SOAP-ENV:Fault>
        <faultcode xsi:type="xsd:string">Client</faultcode>
        <faultstring xsi:type="xsd:string">
            soap request contained mismatching parameters of name inputDate had type string,
            which did not match signature's type: timeInstant
        </faultstring>
        <faultactor xsi:type="xsd:string"></faultactor>
        <faultdetail xsi:type="xsd:string"></faultdetail>
    </SOAP-ENV:Fault>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
 




Copyright (c) by Charles Elkan, 2002.