向前兼容的数据协定

Windows Communication Foundation (WCF) 数据协定系统的一个特征是协定能够以不间断的方式随着时间而逐步演化。 也就是说,具有旧版本数据协定的客户端可以与具有相同数据协定的新版本的服务进行通信,或者具有新版本数据协定的客户端可以与相同数据协定的旧版本进行通信。 有关详细信息,请参阅最佳做法:数据协定版本控制

如果创建了现有数据协定的新版本,您可以根据需要来应用大多数版本管理功能。 但是为了能正常工作,第一版的类型中必须内置一种称为“往返”的版本管理功能。

往返

当数据从数据协定的新版本传递到旧版本,然后传递回新版本时,就发生了往返。 往返保证了数据不会丢失。 如果启用往返功能,则可以使类型向前兼容于数据协定版本管理模型所支持的任何未来更改。

若要对某一特定类型启用往返功能,该类型必须实现 IExtensibleDataObject 接口。 该接口包含一个属性,即 ExtensionData(由 ExtensionDataObject 类型返回)。 该属性存储数据协定未来版本中对当前版本未知的所有数据。

示例

下面的数据协定不向前兼容于未来的更改。

[DataContract]
public class Person
{
    [DataMember]
    public string fullName;
}
<DataContract()> _
Public Class Person
    <DataMember()> _
    Public fullName As String
End Class

若要使该类型兼容于未来的更改(例如添加名为“phoneNumber”的新数据成员),应实现 IExtensibleDataObject 接口。

[DataContract]
public class Person : IExtensibleDataObject
{
    [DataMember]
    public string fullName;
    private ExtensionDataObject theData;

    public virtual ExtensionDataObject ExtensionData
    {
        get { return theData; }
        set { theData = value; }
    }
}
<DataContract()> _
Public Class Person
    Implements IExtensibleDataObject
    <DataMember()> _
    Public fullName As String
    Private theData As ExtensionDataObject


    Public Overridable Property ExtensionData() As _
     ExtensionDataObject Implements _
     IExtensibleDataObject.ExtensionData
        Get
            Return theData
        End Get
        Set
            theData = value
        End Set
    End Property
End Class

当 WCF 基础结构遇到不属于原始数据协定的数据时,该数据被存储在该属性中并保留下来。 除非是临时存储,否则不会以任何其他方式处理该数据。 如果对象返回到它的起始位置,则原始(未知)数据也将返回。 由此,数据完成了从起始终结点又回到起始终结点的往返过程而没有丢失。 但请注意,如果起始终结点要求处理数据,则不会满足这一期望,该终结点必须以某种方式检测并调整更改。

ExtensionDataObject 类型不包含公共方法或属性。 因此,无法直接访问存储在 ExtensionData 属性内部的数据。

通过在 ignoreExtensionDataObject 构造函数中将 true 设置为 DataContractSerializer,或者在 IgnoreExtensionDataObject 中将 true 属性设置为 ServiceBehaviorAttribute,可以关闭往返功能。 当该功能关闭时,反序列化程序将不填充 ExtensionData 属性,序列化程序也不发出该属性的内容。

另请参阅