创建 WSDL 文档
Christine 负责实际的数据,而 Larry 负责在服务及其客户机间传递的实际消息。为了处理这些消息,他创建了 WSDL 文档。
消息
Larry 的第一步是决定服务将实际执行的函数,然后再为服务定义消息。与部门的其他人商议后,他制订了函数及其对应消息的列表,我们将在这一部分的其余内容中讨论这些函数。
createNewAd
此函数在广告结束日期接受广告的内容,并返回新创建的广告的内容(请参见清单 10 和清单 11)。
清单 10. createNewAdRequest(输入)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<req:createNewAdRequest
xmlns:req="http://daily-moon.com/classifieds/">
<req:content>Vintage 1963 T-Bird...</req:content>
<req:endDate>4/30/07</req:endDate>
</req:createNewAdRequest>
</env:Body>
|
清单 11. createNewAdResponse(输出)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<res:createNewAdResponse
xmlns:res="http://daily-moon.com/classifieds/">
<res:newAdId>1138</res:newAdId>
</res:createNewAdResponse>
</env:Body>
|
editExistingAd
此函数接受现有广告,并替换其在数据库中的内容。它将返回一个 Boolean 值声明,指示操作是否成功(请参见清单 12 和清单 13)。
清单 12. editExistingAdRequest(输入)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<req:editExistingAdRequest
xmlns:req="http://daily-moon.com/classifieds/">
<req:ClassifiedAd>
<req:id>1138</req:id>
<req:content>Vintage 1963 T-Bird...</req:content>
<req:startDate>4/1/2007</req:startDate>
<req:endDate>4/30/2007</req:endDate>
<req:ClassifiedAd>
</req:editExistingAdRequest >
</env:Body>
|
清单 13. editExistingAdResponse(输出)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<res:editExistingAdResponse
xmlns:res="http://daily-moon.com/classifieds/">
<res:isOK>true</res:isOK>
</res:editExistingAdResponse>
</env:Body>
|
getExistingAds
此函数将返回现有 ClassifiedAds
的列表(请参见清单 14 和清单 15)。
清单 14. getExistingAdsRequest(输入)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<req:getExistingAdsRequest
xmlns:req="http://daily-moon.com/classifieds/">
</req:getExistingAdsRequest>
</env:Body>
|
清单 15. getExistingAdsResponse(输出)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<res:getExistingAdsResponse
xmlns:res="http://daily-moon.com/classifieds/">
<res:ClassifiedList>
<res:ClassifiedAd>
<res:id>1138</res:id>
<res:content>Vintage 1963 T-Bird...</res:content>
<res:startDate>4/1/2007</res:startDate>
<res:endDate>4/30/2007</res:endDate>
</res:ClassifiedAd>
<res:ClassifiedAd>
<res:id>2883</res:id>
<res:content>Championship playoff
tickets...</res:content>
<res:startDate>4/1/2007</res:startDate>
<res:endDate>4/30/2007</res:endDate>
</res:ClassifiedAd>
</res:ClassifiedList>
</res:getExistingAdsResponse >
</env:Body>
|
finalizeIssue
此函数是“仅输入”的函数,接收最终的发布日期,而并不返回任何数据(请参见清单 16)。
清单 16. finalizeIssueRequest(输入)
<env:Envelope
xmlns:env="http://schemas.xmlSOAP.org/SOAP/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<env:Body>
<req:finalizeIssueRequest
xmlns:req="http://daily-moon.com/classifieds/">
<req:issueDate>4/10/06</req:issueDate>
</req:FinalizeIssueRequest >
</env:Body>
|
有了这些消息后,Larry 开始着手创建实际的 WSDL 文档。
创建基本文档
Larry 首先创建 WSDL 文档的基本框架(请参见清单 17)。
清单 17. 基本 WSDL 文档
<wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
targetNamespace="http://ws.apache.org/axis2">
<wsdl:types>
</wsdl:types>
<wsdl:message name="createNewAdRequestMessage">
</wsdl:message>
<wsdl:portType name="ClassifiedServicePortType">
</wsdl:portType>
<wsdl:binding name="ClassifiedServiceBinding">
</wsdl:binding>
<wsdl:service name="ClassifiedService">
</wsdl:service>
</wsdl:definitions>
|
像其所定义的 SOAP 消息一样,WSDL 也是由 XML 组成的。定义位于 definitions
元素内,如此处所示。首先看下面,您定义了 service
。service
使用一个特殊的 binding
,而后者是 portType
的一个实现。portType
定义操作,而操作由 messages
组成。消息中包含由 types
部分中定义的 XML 组成。
definitions
元素定义两个命名空间。第一个使用前缀 wsdl
:,为组成 WSDL 的实际元素提供命名空间。第二个 targetNamespace
定义 WSDL 定义的项所属的命名空间。
Larry 首先定义的是类型。
定义类型
Larry 拿到 Christine 提供的定义,并将其放入 types
元素中,从而在文档内创建了一个新模式,如清单 18 中所示。
清单 18. 定义类型
<wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:ns1="http://org.apache.axis2/xsd"
targetNamespace="http://ws.apache.org/axis2">
<wsdl:types>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://org.apache.axis2/xsd"
elementFormDefault="unqualified"
attributeFormDefault="unqualified">
<xs:element type="ns1:ClassifiedAd" name="ClassifiedAd" />
<xs:complexType name="ClassifiedAd">
<xs:sequence>
<xs:element type="xs:int" name="id" />
<xs:element type="xs:string" name="content" />
<xs:element type="xs:string" name="endDate" />
<xs:element type="xs:string" name="startDate" />
</xs:sequence>
</xs:complexType>
<xs:element type="ns1:ClassifiedList" name="ClassifiedList" />
<xs:complexType name="ClassifiedList">
<xs:sequence>
<xs:element minOccurs="0" type="ns1:ClassifiedAd"
name="ClassifiedAd" maxOccurs="unbounded" />
</xs:sequence>
</xs:complexType>
<xs:element name="createNewAdRequest">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:string" name="content" />
<xs:element type="xs:string" name="endDate" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="createNewAdResponse">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:int" name="newAdId" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="editExistingAdRequest">
<xs:complexType>
<xs:sequence>
<xs:element type="ns1:ClassifiedAd"
name="ClassifiedAd" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="editExistingAdResponse">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:boolean" name="isOK" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="getExistingAdsRequest">
<xs:complexType />
</xs:element>
<xs:element name="getExistingAdsResponse">
<xs:complexType>
<xs:sequence>
<xs:element type="ns1:ClassifiedList"
name="ClassifiedList" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="finalizeIssueRequest">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:string" name="issueDate" />
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
</wsdl:types>
</wsdl:definitions>
|
从代码的起始处开始,请注意我们有两个命名空间部分。第一个位于 schema
元素本身中。此处 Larry 定义了两个命名空间。第一个命名空间是 XML Schema 命名空间,使用前缀 xs
:。第二个命名空间是 targetNamespace
,定义模式创建的定义所属的命名空间。也就是说,当第二个版本创建名为 ClassifiedAd
的 complexType
时,该定义属于命名空间 http://org.apache.axis2/xsd
。不过,为了引用该命名空间,Larry 需要创建另一个别名。您可以在以 ns1
: 为前缀的 definitions 元素上看到此别名。(Larry 可以直接将该定义放在 schema 元素上,但他稍后需要在 schema 元素外使用此定义。)后面两个属性 elementFormDefault
和 attributeFormDefault
表示元素和属性是否应该有命名空间前缀。
前面四个定义来自 Christine 提供给 Larry 的定义,但其余定义用于定义 Larry 前面创建的消息。
有关命名空间的说明
和许多编程语言一样,在 XML 中,经常有必要为各种元素和属性指定“命名空间”。这样就能方便地对具有相同名称但用途不同(来源也可能不同)的元素进行区分。XML 通过 URI 引用命名空间。例如,XML 模式命名空间为 http://www.w3.org/2001/XMLSchema
。不过,为了方便起见,还为其分配了一个别名(或前缀)。例如,此处的模式命名空间的前缀为 xs:
。请记住,别名只是一个别名而已,重要的是 URI。因此,属于 ns1:
命名空间的元素或属性也是模式的 targetNamespace
的一部分。
创建消息
定义了各个类型后,Larry 就可以定义将在 SOAP 信封中来回传递的消息了(请参见清单 19)。
清单 19. 创建消息
<wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:ns1="http://org.apache.axis2/xsd"
targetNamespace="http://ws.apache.org/axis2">
<wsdl:types>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://org.apache.axis2/xsd"
elementFormDefault="unqualified"
attributeFormDefault="unqualified">
...
<xs:element name="createNewAdRequest">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:string" name="content" />
<xs:element type="xs:string" name="endDate" />
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="createNewAdResponse">
<xs:complexType>
<xs:sequence>
<xs:element type="xs:int" name="newAdId" />
</xs:sequence>
</xs:complexType>
</xs:element>
...
</xs:schema>
</wsdl:types>
<wsdl:message name="createNewAdRequestMessage">
<wsdl:part name="part1" element="ns1:createNewAdRequest"
/>
</wsdl:message>
<wsdl:message name="createNewAdResponseMessage">
<wsdl:part name="part1" element="ns1:createNewAdResponse" />
</wsdl:message>
<wsdl:message name="getExistingAdsResponseMessage">
<wsdl:part name="part1" element="ns1:getExistingAdsResponse" />
</wsdl:message>
<wsdl:message name="editExistingAdRequestMessage">
<wsdl:part name="part1" element="ns1:editExistingAdRequest" />
</wsdl:message>
<wsdl:message name="getExistingAdsRequestMessage">
<wsdl:part name="part1" element="ns1:getExistingAdsRequest" />
</wsdl:message>
<wsdl:message name="editExistingAdResponseMessage">
<wsdl:part name="part1" element="ns1:editExistingAdResponse" />
</wsdl:message>
<wsdl:message name="finalizeIssueRequestMessage">
<wsdl:part name="part1" element="ns1:finalizeIssueRequest" />
</wsdl:message>
<wsdl:portType name="ClassifiedServicePortType">
</wsdl:portType>
<wsdl:binding name="ClassifiedServiceBinding">
</wsdl:binding>
<wsdl:service name="ClassifiedService">
</wsdl:service>
</wsdl:definitions>
|
每个消息都具有一个 name
,以便稍后对其进行引用。在每个消息内,您可以定义一个或多个 part
。请注意,WSDL 2.0 仅允许每个 message
包含一个 part
,因此 Larry 此处严格遵循了此约定。
每个 part
都有一个 name
,而由 element
的名称组成该 part
。元素名称将反过来引用在 types
元素中定义的类型。请注意,元素的名称以 ns1:
为前缀,即与模式的 targetNamespace
匹配的命名空间前缀。也就是说,当 Larry 创建 createNewAdResponse
的定义时,该定义进入了 http://org.apache.axis2/xsd namespace
中,由于前缀 ns1:
也引用此命名空间,因此现在可以使用该前缀引用此命名空间。
定义接口 (portType)
消息本身并不会带来什么好处,因此 Larry 需要将其与特定的操作关联。这些 operation
属于 portType
的一部分。portType
仅包含定义,而不包含实现。就这个意义而言,它与接口很相似。事实上,在 WSDL 2.0 中,portType
的名称已更改为 interface
。Larry 为每个功能创建了一个操作(请参见清单 20)。
清单 20. 添加操作
<wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:tns=http://ws.apache.org/axis2
xmlns:ns1="http://org.apache.axis2/xsd"
targetNamespace="http://ws.apache.org/axis2">
<wsdl:types>
...
</wsdl:types>
<wsdl:message name="createNewAdRequestMessage">
<wsdl:part name="part1" element="ns1:createNewAdRequest" />
</wsdl:message>
<wsdl:message name="createNewAdResponseMessage">
<wsdl:part name="part1" element="ns1:createNewAdResponse" />
</wsdl:message>
...
<wsdl:message name="finalizeIssueRequestMessage">
<wsdl:part name="part1" element="ns1:finalizeIssueRequest" />
</wsdl:message>
<wsdl:portType name="ClassifiedServicePortType">
<wsdl:operation name="finalizeIssue">
<wsdl:input message="tns:finalizeIssueRequestMessage" />
</wsdl:operation>
<wsdl:operation name="createNewAd">
<wsdl:input message="tns:createNewAdRequestMessage" />
<wsdl:output message="tns:createNewAdResponseMessage" />
</wsdl:operation>
<wsdl:operation name="editExistingAd">
<wsdl:input message="tns:editExistingAdRequestMessage" />
<wsdl:output message="tns:editExistingAdResponseMessage" />
</wsdl:operation>
<wsdl:operation name="getExistingAds">
<wsdl:input message="tns:getExistingAdsRequestMessage" />
<wsdl:output message="tns:getExistingAdsResponseMessage" />
</wsdl:operation>
</wsdl:portType>
<wsdl:binding name="ClassifiedServiceBinding">
</wsdl:binding>
<wsdl:service name="ClassifiedService">
</wsdl:service>
</wsdl:definitions>
|
Larry 创建了两种类型的消息。一类消息(如 finalizeIssue
)是“仅输入”的操作,因为它仅具有输入消息。消息 finalizeIssueRequest
是前面定义的,和前面一样,我们将创建一个新前缀 tns:
来引用其所属的命名空间。
第二种操作类型是请求/响应操作,如 createNewAd
。在这种情况下,Larry 将同时定义输入和输出消息。
定义绑定
如果 portType
像接口,则 binding
为该接口的实现(请参见清单 21)。
清单 21. 创建绑定
<wsdl:definitions
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:tns="http://ws.apache.org/axis2"
xmlns:ns1="http://org.apache.axis2/xsd"
targetNamespace="http://ws.apache.org/axis2">
<wsdl:types>
</wsdl:types>
<wsdl:message name="createNewAdRequestMessage">
<wsdl:part name="part1" element="ns1:createNewAdRequest" />
</wsdl:message>
...
<wsdl:portType name="ClassifiedServicePortType">
<wsdl:operation name="finalizeIssue">
<wsdl:input message="tns:finalizeIssueRequestMessage" />
</wsdl:operation>
<wsdl:operation name="createNewAd">
<wsdl:input message="tns:createNewAdRequestMessage" />
<wsdl:output message="tns:createNewAdResponseMessage" />
</wsdl:operation>
<wsdl:operation name="editExistingAd">
<wsdl:input message="tns:editExistingAdRequestMessage" />
<wsdl:output message="tns:editExistingAdResponseMessage" />
</wsdl:operation>
<wsdl:operation name="getExistingAds">
<wsdl:input message="tns:getExistingAdsRequestMessage" />
<wsdl:output message="tns:getExistingAdsResponseMessage" />
</wsdl:operation>
</wsdl:portType>
<wsdl:binding name="ClassifiedServiceBinding"
type="tns:ClassifiedServicePortType">
<soap:binding transport="http://schemas.xmlsoap.org/soap/http"
style="document" />
<wsdl:operation name="createNewAd">
<soap:operation soapAction="createNewAd" style="document" />
<wsdl:input>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:output>
</wsdl:operation>
<wsdl:operation name="finalizeIssue">
<soap:operation soapAction="finalizeIssue" style="document" />
<wsdl:input>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:input>
</wsdl:operation>
<wsdl:operation name="editExistingAd">
<soap:operation soapAction="editExistingAd" style="document" />
<wsdl:input>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:output>
</wsdl:operation>
<wsdl:operation name="getExistingAds">
<soap:operation soapAction="getExistingAds" style="document" />
<wsdl:input>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:output>
</wsdl:operation>
</wsdl:binding>
<wsdl:service name="ClassifiedService">
</wsdl:service>
</wsdl:definitions>
|
首先,请注意绑定 type
引用 Larry 已经创建的 ClassifiedServicePortType
。其次,请注意添加了 soap:
命名空间。此 binding
用于 HTTP 上的 SOAP 消息,如 soap:binding
元素中所示。请注意 transport
属性。(尚不用担心 style
,我们将在接下来的部分中对其进行讨论。)
对于共享其在 portType
中的名称的每个操作,Larry 现在都要添加一个 soap:operation
元素。此元素执行两个操作。根据此元素的说明,第一个操作实际上是 SOAP 操作。第二个操作用于指定 soapAction
,此为在实际 SOAP 消息前发送的 HTTP Header。服务器可以使用此 Header 来将请求路由到相应的操作。
请注意,soapAction
始终有一定的问题,虽然在 WSDL 1.1 是可选的,但已经完全从 WSDL 2.0 中删除了。
每个操作还定义 input
和 output
消息(或者,使用仅输入的消息时,只定义 input
消息),但现在 Larry 还将添加特定的 SOAP 信息。同样,不用担心 use
属性;我们也将在稍后讨论此属性。此元素还为有效负载的内容定义命名空间。
定义服务
定义了接口和绑定后,接下来就要定义服务了(请参见清单 22)。
清单 22. 定义服务
...
<wsdl:binding name="ClassifiedServiceBinding"
type="tns:ClassifiedServicePortType">
...
</wsdl:binding>
<wsdl:service name="ClassifiedService">
<wsdl:port name="ClassifiedServicePort"
binding="tns:ClassifiedServiceBinding">
<soap:address location=
"http://127.0.0.1:8080/axis2/services/ClassifiedService" />
</wsdl:port>
</wsdl:service>
</wsdl:definitions>
|
service
可以具有多个端点,每个端点都由其自己对应的 port
元素进行定义。port
元素与特定绑定对应,包括有关如何访问此绑定的信息。在本例中,Larry 指定可以通过 SOAP 在以下位置访问该端口:http://127.0.0.1:8080/axis2/services/ClassifiedService
。
为服务添加注释
定义了服务后,还要进行一个步骤。虽然是可选的,但真的应该进行此步骤。WSDL 允许您向 WSDL 文档中的任何元素添加 documentation 元素。清单 23 提供了一个示例。
清单 23. 为服务添加注释
...
<wsdl:portType name="ClassifiedServicePortType">
<wsdl:document>The finalizeIssue operation is an "in-only"
operation that tells the system not to accept any
more ads for a particular date.</wsdl:document>
<wsdl:operation name="finalizeIssue">
<wsdl:input message="tns:finalizeIssueRequestMessage" />
</wsdl:operation>
...
|
有关 WSDL 的知识还有很多,但上面这些是基本的内容。不过,继续学习本教程之前,让我们了解一些您可能遇到的更为复杂的情况。
绑定 SOAP over HTTP 之外的其他协议
尽管 WSDL 的最常见用法是定义 SOAP over HTTP,但却不是指定 Web 服务的唯一方法。例如,Larry 可以创建一个使用 SOAP over E-mail 的绑定,并仅为 finalizeIssue
操作启用它(请参见清单 24)。
清单 24. 添加其他绑定
...
<wsdl:binding name="ClassifiedServiceEmailBinding"
type="tns:ClassifiedServicePortType">
<soap:binding style="document" transport="http://example.com/smtp"/>
<wsdl:operation name="finalizeIssue">
<wsdl:input message="tns:finalizeIssueRequestMessage">
<soap:body parts="body" use="literal"/>
</wsdl:input>
</wsdl:operation>
</wsdl:binding>
<wsdl:service name="ClassifiedService">
<wsdl:port name="ClassifiedServicePort"
binding="tns:ClassifiedServiceBinding">
<soap:address location=
"http://127.0.0.1:8080/axis2/services/ClassifiedService" />
</wsdl:port>
<wsdl:port name="ClassifiedServiceEmailPort"
binding="tns:ClassifiedServiceEmailBinding">
<soap:address location="mailto:finalizeIssue@daily-moon.com" />
</wsdl:port>
</wsdl:service>
</wsdl:definitions>
|
此处 Larry 添加了第二个绑定 ClassifiedServiceEmailBinding
。和 ClassifiedServiceBinding
绑定一样,此绑定基于 ClassifiedServicePortType portType
。不过,在本例中,他使用的是 SMTP(用于发送电子邮件的协议),而不是 HTTP。他可以随后向服务添加第二个端口,使其基于新绑定,使用电子邮件 URL 作为地址,而不是 HTTP URL。您可以为单个服务创建任意多的端口。
SOAP 和 Mime
另一个与此解决方案有关的主题还不甚明显,即将 SOAP 用于附件。由于消息不仅是 XML 文档,您应该如何使用 WSDL 进行指定呢?这个问题的答案涉及到一个事实,即消息是使用“多部分 MIME”发送的。幸运的是,您可以在 WSDL 文档中指定这一点。例如,Larry 希望指定一个操作,通过此操作,用户可以编辑从广告的 PDF 校样获得的现有广告(请参见清单 25)。
>清单 25. 指定包含多个部分的消息
...
<wsdl:operation name="editExistingAd">
<soap:operation soapAction="editExistingAd"
style="document" />
<wsdl:input>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
</wsdl:input>
<wsdl:output>
<soap:body use="literal"
namespace="http://daily-moon.com/classifieds" />
<mime:multipartRelated>
<mime:part>
<soap:body parts="body" use="literal"/>
</mime:part>
<mime:part>
<mime:content part="docs" type="text/html"/>
</mime:part>
<mime:part>
<mime:content part="proof" type="image/gif"/>
<mime:content part="proof" type="image/jpeg"/>
</mime:part>
</mime:multipartRelated>
</wsdl:output>
...
|
在本例中,返回消息包含 SOAP、一个 HTML 文档和两个图像文件。
WSDL 2.0 中包含的新内容
在此部分中,我尽力说明 WSDL 2.0 与 WSDL 1.1 的一些不同之处,如从可能出现多个 portType
的情况变为单个 interface
,以及 message
不再能包含多个部分等。其他方面也有一定程度的调整。
有多个因素促成了这些更改,但大部分更改的目的都是为了提高互操作性——不符合 WS-I 基本概要 (WS-I Basic Profile) 的构造通常都禁止使用——或为了更方便地将 WSDL 与经过扩展的 SOAP 规范一起使用。例如,WSDL 2.0 更多使用的是“组件”模型,此模型更适合与 WS-Choreography 等规范的要求进行集成。
另一个更改与“消息交换模式”的正式规范有关。WSDL 2.0 不依赖于用户确定是同时存在输入和输出还是仅有一个输入消息,它允许您具体地声明所使用的模式(请参见清单 26)。
清单 26. 指定消息交换模式
...
<wsdl:operation name="finalizeIssue"
pattern=http://www.w3.org/2006/01/wsdl/in-only">
<wsdl:input message="tns:finalizeIssueRequestMessage" />
</wsdl:operation>
<wsdl:operation name="createNewAd"
pattern="http://www.w3.org/2006/01/wsdl/in-out">
<wsdl:input message="tns:createNewAdRequestMessage" />
<wsdl:output message="tns:createNewAdResponseMessage" />
</wsdl:operation>
...
|
现在让我们深入了解一下 WSDL 样式。
posted on 2006-12-29 19:09
SIMONE 阅读(1623)
评论(0) 编辑 收藏 所属分类:
AXIS 、
JAVA