簡體   English   中英

繼承更改的DataContract

[英]DataContract with inheritance change

我正在使用DataContracts來序列化對象。 假設我已經序列化了以這種方式構建的數據:

[DataContract]
public class Dog : IExtensibleDataObject
{
    [DataMember]
    public int age;

    [DataMember]
    public string name;

    ExtensionDataObject IExtensibleDataObject.ExtensionData { get; set; }
}

現在我正在改變我的架構,我想用這些類讀取以前的序列化數據:

[DataContract]
[KnownType(typeof(Dog))]
public class Animal : IExtensibleDataObject
{
    [DataMember]
    public string name;

    ExtensionDataObject IExtensibleDataObject.ExtensionData { get; set; }
}

[DataContract]
public class Dog : Animal
{
    [DataMember]
    public int age;
}

但我獲得name = null。 我知道這取決於順序:文件首先保存為age,然后從name開始讀取,因為它在基類上。
有沒有辦法處理這個,可能是通過改變順序?

我不認為這是可能的。

過去的xml本來就是

<dog>
    <name>Bob</name>
    <age>10</age>
</dog>

它現在期待

<animal>
    <name>Bob</name>
    <dog>
        <age>10</age>
    </dog>
</animal>

對於在新DataContract上序列化的任何內容,該屬性更高。 使用IExtensibleDataObject方法更改繼承層次結構是一個重大變化。

允許繼承與數據協定一起使用,前提是繼承不用作版本控制機制並遵循某些規則。 如果類型派生自某個基類型,請不要在未來版本中從不同的基類型派生(除非它具有相同的數據協定)。 這有一個例外:您可以在數據協定類型與其基本類型之間的層次結構中插入一個類型,但前提是它不包含與其他類型的任何可能版本中的其他成員具有相同名稱的數據成員。層次結構。 通常,在同一繼承層次結構的不同級別使用具有相同名稱的數據成員可能會導致嚴重的版本控制問題,應該避免使用。

更多最佳實踐:數據合同版本控制

編輯1:

您也許可以嘗試在Animal中創建名稱虛擬並在Dog中覆蓋它? 或者一些瘋狂的方法來強制序列化的新版本在dog下有名字。 即,像,

[DataContract] 
[KnownType(typeof(Dog))] 
public class Animal : IExtensibleDataObject 
{
    public virtual string name; 

    ExtensionDataObject IExtensibleDataObject.ExtensionData { get; set; } 
} 

[DataContract] 
public class Dog : Animal 
{ 
    [DataMember] 
    public override string name; 

    [DataMember] 
    public int age; 
} 

您應該查看本SO帖子中討論的WCF合同版本控制

基本上,您需要在ServiceContract上分配一個Namespace ,如果您希望在合同發展時需要向后兼容性,請保留舊版本和舊版本。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM