XML Web 服务的 XML 序列化

XML 序列化是 XML Web 服务结构中使用的基础传输机制,它由 XmlSerializer 类执行。要控制由 XML Web 服务生成的 XML,可将控制 XML 序列化的属性控制编码的 SOAP 序列化的属性中列出的属性应用于在创建 XML Web 服务 (.asmx) 时使用的文件的类、返回值、参数和字段。有关创建 XML Web 服务的更多信息,请参见使用 ASP.NET 的 XML Web 服务

文本样式和编码样式

XML Web 服务生成的 XML 可以采用文本和编码这两种格式中的任意一种,自定义 SOAP 消息的格式中对此作了讲解。因此,有两组控制 XML 序列化的属性。控制 XML 序列化的属性中列出的属性专门用于控制文本样式 XML。控制编码的 SOAP 序列化的属性中列出的属性控制编码样式。通过有选择性地应用这些属性,可将应用程序调整为返回两种样式中的任一种或同时返回两种。另外,这些属性可(根据需要)应用于返回值和参数。

使用两种样式的示例

当您在创建 XML Web 服务时,可同时使用方法的两组属性。在下面的代码示例中,名为 MyService 的类包含两个 XML Web 服务方法:MyLiteralMethodMyEncodedMethod。两个方法执行同样的功能:返回 Order 类的实例。在 Order 类中,XmlTypeAttributeSoapTypeAttribute 两个特性都应用于 OrderID 字段,两个特性的 ElementName 属性设置为不同的值。

要运行该示例,请将该代码粘贴到带有 .asmx 扩展名的文件中,并将该文件放入由 Internet 信息服务 (IIS) 管理的虚拟目录中。在 HTML 浏览器(如 Internet Explorer)中,键入计算机的名称、虚拟目录名和文件名。

<%@ WebService Language="VB" Class="MyService" %>
Imports System
Imports System.Web.Services
Imports System.Web.Services.Protocols
Imports System.Xml.Serialization
Public Class Order
    ' Both types of attributes can be applied. Depending on which type
    ' the method used, either one will affect the call.
    <SoapElement(ElementName:= "EncodedOrderID"), _
    XmlElement(ElementName:= "LiteralOrderID")> _
    public OrderID As String
End Class

Public Class MyService
    <WebMethod, SoapDocumentMethod> _
    public Function MyLiteralMethod() As Order 
        Dim myOrder As Order = New Order()
        return myOrder
    End Function
    <WebMethod, SoapRpcMethod> _
    public Function MyEncodedMethod() As Order 
        Dim myOrder As Order = New Order()
        return myOrder
    End Function
End Class
<%@ WebService Language="C#" Class="MyService" %>
using System;
using System.Web.Services;
using System.Web.Services.Protocols;
using System.Xml.Serialization;
public class Order{
    // Both types of attributes can be applied. Depending on which type
    // the method used, either one will affect the call.
    [SoapElement(ElementName = "EncodedOrderID")]
    [XmlElement(ElementName = "LiteralOrderID")]
    public String OrderID;
}
public class MyService{
    [WebMethod][SoapDocumentMethod]
    public Order MyLiteralMethod(){
        Order myOrder = new Order();
        return myOrder;
    }
    [WebMethod][SoapRpcMethod]
    public Order MyEncodedMethod(){
        Order myOrder = new Order();
        return myOrder;
    }
}

下面的代码示例调用 MyLiteralMethod。元素名被更改为“LiteralOrderID”。

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="https://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body>
        <MyLiteralMethodResponse xmlns="http://tempuri.org/">
            <MyLiteralMethodResult>
                <LiteralOrderID>string</LiteralOrderID>
            </MyLiteralMethodResult>
        </MyLiteralMethodResponse>
    </soap:Body>
</soap:Envelope>

下面的代码示例调用 MyEncodedMethod。元素名为“EncodedOrderID”。

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soapenc="https://schemas.xmlsoap.org/soap/encoding/" xmlns:tns="http://tempuri.org/" xmlns:types="http://tempuri.org/encodedTypes" xmlns:soap="https://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body soap:encodingStyle="https://schemas.xmlsoap.org/soap/encoding/">
        <tns:MyEncodedMethodResponse>
            <MyEncodedMethodResult href="#id1" />
        </tns:MyEncodedMethodResponse>
        <types:Order id="id1" xsi:type="types:Order">
            <EncodedOrderID xsi:type="xsd:string">string</EncodedOrderID>
        </types:Order>
    </soap:Body>
</soap:Envelope>

将属性应用于返回值

还可将属性应用于返回值,以控制命名空间、元素名等。下面的代码示例将 XmlElementAttribute 属性应用于 MyLiteralMethod 方法的返回值。这样做使您得以控制命名空间和元素名。

    <WebMethod, SoapDocumentMethod> _
    public Function MyLiteralMethod() As _
    <XmlElement(Namespace:="http://www.cohowinery.com", _
    ElementName:= "BookOrder")> _
    Order 
        Dim myOrder As Order = New Order()
        return myOrder
    End Function
    [return: XmlElement(Namespace = "http://www.cohowinery.com",
    ElementName = "BookOrder")]
    [WebMethod][SoapDocumentMethod]
    public Order MyLiteralMethod(){
        Order myOrder = new Order();
        return myOrder;
    }

当被调用时,该代码返回类似于以下代码的 XML。

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="https://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body>
        <MyLiteralMethodResponse xmlns="http://tempuri.org/">
            <BookOrder xmlns="http://www.cohowinery.com">
                <LiteralOrderID>string</LiteralOrderID>
            </BookOrder>
        </MyLiteralMethodResponse>
    </soap:Body>
</soap:Envelope>

将属性应用于参数

还可将属性应用于参数,以指定命名空间、元素名等。下面的代码示例将一个参数添加到 MyLiteralMethodResponse 方法,并将 XmlAttributeAttribute 属性应用于该参数。元素名和命名空间都为该参数进行了设置。

    <WebMethod, SoapDocumentMethod> _
    public Function MyLiteralMethod(<XmlElement _
    ("MyOrderID", Namespace:="https://www.microsoft.com")>ID As String) As _
    <XmlElement(Namespace:="http://www.cohowinery.com", _
    ElementName:= "BookOrder")> _
    Order 
        Dim myOrder As Order = New Order()
        myOrder.OrderID = ID
        return myOrder
    End Function
    [return: XmlElement(Namespace = "http://www.cohowinery.com",
    ElementName = "BookOrder")]
    [WebMethod][SoapDocumentMethod]
    public Order MyLiteralMethod([XmlElement("MyOrderID", 
    Namespace="https://www.microsoft.com")] string ID){
        Order myOrder = new Order();
        myOrder.OrderID = ID;
        return myOrder;
    } 

SOAP 请求将类似于下面的代码。

<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="https://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body>
        <MyLiteralMethod xmlns="http://tempuri.org/">
            <MyOrderID xmlns="https://www.microsoft.com">string</MyOrderID>
        </MyLiteralMethod>
    </soap:Body>
</soap:Envelope>

将属性应用于类

如果需要控制与类相关的元素的命名空间,可根据需要应用 XmlTypeAttributeXmlRootAttributeSoapTypeAttribute。下面的代码示例将这三个属性都应用于 Order 类。

<XmlType("BigBookService"), _
SoapType("SoapBookService"), _
XmlRoot("BookOrderForm")> _
Public Class Order
    ' Both types of attributes can be applied. Depending on which
    ' the method used, either one will affect the call.
    <SoapElement(ElementName:= "EncodedOrderID"), _
    XmlElement(ElementName:= "LiteralOrderID")> _
    public OrderID As String
End Class
[XmlType("BigBooksService", Namespace = "http://www.cpandl.com")]
[SoapType("SoapBookService")]
[XmlRoot("BookOrderForm")]
public class Order{
    // Both types of attributes can be applied. Depending on which
    // the method used, either one will affect the call.
    [SoapElement(ElementName = "EncodedOrderID")]
    [XmlElement(ElementName = "LiteralOrderID")]
    public String OrderID;
}

应用 XmlTypeAttributeSoapTypeAttribute 的结果可在您检查服务描述时看到,如下面的代码示例所示。

    <s:element name="BookOrderForm" type="s0:BigBookService" /> 
- <s:complexType name="BigBookService">
- <s:sequence>
    <s:element minOccurs="0" maxOccurs="1" name="LiteralOrderID" type="s:string" /> 
    </s:sequence>

- <s:schema targetNamespace="http://tempuri.org/encodedTypes">
- <s:complexType name="SoapBookService">
- <s:sequence>
    <s:element minOccurs="1" maxOccurs="1" name="EncodedOrderID" type="s:string" /> 
    </s:sequence>
    </s:complexType>
    </s:schema>

XmlRootAttribute 的效果也可以在 HTTP GET 和 HTTP POST 的结果中看到,如下所示。

<?xml version="1.0" encoding="utf-8"?>
<BookOrderForm xmlns="http://tempuri.org/">
    <LiteralOrderID>string</LiteralOrderID>
</BookOrderForm>

请参见

任务

如何:将对象序列化为 SOAP 编码的 XML 流
如何:重写已编码的 SOAP XML 序列化
如何:将对象序列化
如何:将对象反序列化

概念

控制编码的 SOAP 序列化的属性
介绍 XML 序列化

其他资源

XML 和 SOAP 序列化