2012-03-20 30 views
8

我對DataContractSerializer的行爲感到莫名其妙。我們的配置是基於XML的。 XML用作DataContractSerializer.ReadObject方法的源。最近,當反序列化對象的某些屬性未設置時,我遇到了一個問題。我跟蹤了這​​些更改,發現這些屬性已手動添加到XML中。我認爲這是可以的。很顯然,DataContractSerializer的觀點並不正確,因爲它似乎期望XML節點按字母順序排列。真?!反序列化似乎非常簡單 - 順序讀取XML,解析節點名稱,設置相應的屬性。訂購的目的是什麼?DataContract反序列化由於XML節點的排序不正確而失敗

是否有解決方法?也許某種DataContractSerializer的設置?

回答

3

我最近遇到這個問題。要解決它,我用了XmlSerializer,並移除了XmlElement屬性明確的排序:

set proxy_tool="C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SvcUtil.exe" /nologo /t:code /ser:XmlSerializer /UseSerializerForFaults 
set sed_tool="$(ProjectDir)sed.exe" -r -i "s/,?[[:space:]]*Order=[[:digit:]]+//" 

%proxy_tool% /o:"Proxy1.cs" /n:*,Namespaces.Name1 "Proxy1.wsdl" 
%sed_tool% "Proxy1.cs" 

%proxy_tool% /o:"Proxy2.cs" /n:*,Namespaces.Name2 "Proxy2.wsdl" 
%sed_tool% "Proxy2.cs" 

... 

有一些more information on my blog post

如果你想知道爲什麼秩序的問題,這是因爲在XSD一個sequence有一個定義的順序,和網絡服務合同與XSD定義。

the specification

該定義的結果是,在一個實例,其類型被聲明爲校舍地址出現(例如在SHIPTO PO.xml而)任何元件必須由五個元素和一個屬性。這些元素必須被稱爲名稱,街道,城市,州和郵政編碼,由聲明的名稱屬性的值指定,並且元素必須以聲明它們的相同順序(順序)出現。

+0

哇......這太複雜了。但謝謝你的答案。我結束了嘗試DataContractSerializer,它對我更好。 – Schultz9999 2012-03-23 16:41:14

+0

有沒有辦法可以在DataContract中使用「xs:all」定義?那麼順序無關緊要? – Nicholi 2012-04-10 18:02:49

+0

@Nicholi也許你可以控制WSDL – 2012-04-11 07:06:06

3

您可以使用DataMemberAttribute的Order成員來解決這個問題,但在大多數情況下:XML是針對特定於訂單的(對於元素而非屬性) - 因此它並不是特別錯誤。這說:如果你想要對XML序列化進行精細控制,DataContractSerializer是一個糟糕的選擇XmlSerializer提供了更多的控制 - 而且不那麼挑剔重新訂購iirc。

+0

我明白了你的觀點。我猜我在這種情況下很懶,因爲相同的對象被用作基於WCF的服務的參數,所以不用考慮兩種序列化方式。 – Schultz9999 2012-03-20 23:06:04