WSDL 快速上手
WSDL 是什么
一份 WSDL(Web Service Description Language) 文件就是一份对 Web Service 接口进行定义的文档。
WSDL 提供了什么
- 提供了哪些服务接口
- 接口的消息格式是怎么样的
服务接口
WSDL 使用 <service>
服务元素来定义服务接口,而 WSDL 将服务接口细分了四层:
- 一个 WSDL 文件可以定义多个
<service>
服务元素 - 一个
<service>
元素内可以有多个<port>
端口元素 - 一个
<port>
元素与<binding>
元素是一一对应关系,一个<binding>
元素指定了一个<portType>
元素的三个属性:- 具体协议(HTTP或SOAP等)
transport="http://schemas.xmlsoap.org/soap/http"
- 如果指定协议为 HTTP,则还需要设置
soapAction
属性,比如<soap:operation soapAction="http://example.com/GetLastTradePrice">
。该属性可设置为空,如果该属性设置了非空值,那么必须在 HTTP 请求的 Headers 中附加SOAPAction: "http://example.com/GetLastTradePrice"
字段。
- 如果指定协议为 HTTP,则还需要设置
- 消息传递样式
style="document"
- 编码样式
use="literal"
- 具体协议(HTTP或SOAP等)
- 一个
<portType>
元素里面可以有多个<operation>
,每个<operation>
元素中可选三个子元素,其中每一个子元素都一一对应一个<message>
消息格式元素:<input>
元素,指定一个输入消息格式<message>
元素。必选<output>
元素,指定一个输出消息格式<message>
元素。当不需要返回消息时可不选<fault>
元素,指定一个错误发生时消息格式<message>
元素。不需要指定错误格式时可不选
示例:
<!-- 示例来源:https://www.w3.org/TR/wsdl.html -->
<?xml version="1.0"?>
<definitions name="StockQuote"
targetNamespace="http://example.com/stockquote.wsdl"
xmlns:tns="http://example.com/stockquote.wsdl"
xmlns:xsd1="http://example.com/stockquote.xsd"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns="http://schemas.xmlsoap.org/wsdl/">
<message name="SubscribeToQuotes">
<part name="body" element="xsd1:SubscribeToQuotes"/>
<part name="subscribeheader" element="xsd1:SubscriptionHeader"/>
</message>
<portType name="StockQuotePortType">
<operation name="SubscribeToQuotes">
<input message="tns:SubscribeToQuotes"/>
</operation>
</portType>
<binding name="StockQuoteSoap" type="tns:StockQuotePortType">
<soap:binding style="document" transport="http://example.com/smtp"/>
<operation name="SubscribeToQuotes">
<input message="tns:SubscribeToQuotes">
<soap:body parts="body" use="literal"/>
<soap:header message="tns:SubscribeToQuotes" part="subscribeheader" use="literal"/>
</input>
</operation>
</binding>
<service name="StockQuoteService">
<port name="StockQuotePort" binding="tns:StockQuoteSoap">
<soap:address location="mailto:subscribe@example.com"/>
</port>
</service>
<types>
<schema targetNamespace="http://example.com/stockquote.xsd"
xmlns="http://www.w3.org/2000/10/XMLSchema">
<element name="SubscribeToQuotes">
<complexType>
<all>
<element name="tickerSymbol" type="string"/>
</all>
</complexType>
</element>
<element name="SubscriptionHeader" type="uriReference"/>
</schema>
</types>
</definitions>
在 Java 实现中,与 Java 类的对应关系
在 Java 实现中,一个 Java 具体类只能对应到一个 <binding>
元素,也可以说是 <portType>
元素。而具体类的方法则对应 <portType>
元素中的 <operation>
元素。
消息格式
WSDL 的 <message>
元素就是用来定义消息格式的,而 WSDL 将消息格式又细分了两层:
- 一个
<message>
元素可以有多个<part>
标签,每个<part>
元素一对一指定使用哪一个<types>
元素中定义的<element>
元素 - 一个
<types>
元素定义的<element>
元素内部是嵌套定义的<element>
元素,而<element>
有两类:- 基本值,比如
int
或string
- 复合值,也就是里面嵌套了一个或多个基本值或复合值
<complexType>
元素
- 基本值,比如
示例:
<!-- 示例来源:https://www.w3.org/TR/wsdl.html#_types -->
<definitions .... >
<types>
<schema .... >
<element name="PO" type="tns:POType"/>
<complexType name="POType">
<all>
<element name="id" type="string/>
<element name="name" type="string"/>
<element name="items">
<complexType>
<all>
<element name="item" type="tns:Item" minOccurs="0" maxOccurs="unbounded"/>
</all>
</complexType>
</element>
</all>
</complexType>
<complexType name="Item">
<all>
<element name="quantity" type="int"/>
<element name="product" type="string"/>
</all>
</complexType>
<element name="Invoice" type="tns:InvoiceType"/>
<complexType name="InvoiceType">
<all>
<element name="id" type="string"/>
</all>
</complexType>
</schema>
</types>
<message name="PO">
<part name="po" element="tns:PO"/>
<part name="invoice" element="tns:Invoice"/>
</message>
</definitions>
注意事项
- 当
<binding>
元素中指定了<mesaage>
的<part>
编码样式为literal
字面值时,如果要在<part>
中传入嵌套的 XML 字符串,则里面的所有尖括号对<>
都要转义成对应的<>
。