2010-11-12 120 views
4

我有下面的类:C#反序列化问题

/// <remarks/> 
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.Xml", "4.0.30319.1")] 
[System.SerializableAttribute()] 
[System.Diagnostics.DebuggerStepThroughAttribute()] 
[System.ComponentModel.DesignerCategoryAttribute("code")] 
[System.Xml.Serialization.XmlTypeAttribute(Namespace="urn:eu.emsa.ssn")] 
public partial class SSN_ReceiptType { 

    private Header1Type headerField; 

    /// <remarks/> 
    [System.Xml.Serialization.XmlElementAttribute(Order=0)] 
    public Header1Type Header { 
     get { 
      return this.headerField; 
     } 
     set { 
      this.headerField = value; 
     } 
    } 
} 

而下面的XML:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?> 
    <SSN_Receipt xmlns="urn:eu.emsa.ssn"> 
     <Header StatusMessage="SomethingSomething" StatusCode="Blabla" SSNRefId="N/A" MSRefId="2674762" Version="2.0" To="NCANOHAU1" SentAt="2010-11-12T14:48:44Z" From="SSN"/> 
    </SSN_Receipt> 

而且我用这个类型化的方法来反序列化(通过调用反序列化<SSN_ReceiptType>(xmlGoesHere)) :

/// <summary> 
    /// Deserialize xml string to object of type T 
    /// </summary> 
    /// <typeparam name="T"></typeparam> 
    /// <param name="xml"></param> 
    /// <returns></returns> 
    public static T Deserialize<T>(string xml) 
    { 
     try 
     { 

      // Create serializer 
      var xs = new XmlSerializer(typeof(T)); 

      // Deserialize 
      T t = (T)xs.Deserialize(new StringReader(xml)); 

      return t; 
     } 
     catch (Exception e) 
     { 
      log.Error(string.Format("Unable to deserialize XML: {0}", xml), e); 

      return default(T); 
     } 
    } 

现在,这里是踢球者。这用于工作。但最近我们收到了XSD的新版本用来生成类,并生成新的代码后(这是该类不变,上面看到的)尝试反序列化时,我收到以下异常:

System.SystemException: “有XML文档中的误差(1,57)”

进而:

System.InnerException:< SSN_Receipt的xmlns = '瓮:eu.emsa.ssn'预计不会出现>。

到底是什么? :S我试着添加一个指定“SSN_Receipt”的XmlRootAttribute,这并没有帮助一点。任何人都知道发生了什么事?

更新:从XSD相关章节:

<?xml version="1.0" encoding="UTF-8"?> 
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" 
    xmlns:ssn="urn:eu.emsa.ssn" 
    attributeFormDefault="unqualified" 
    elementFormDefault="qualified" 
    targetNamespace="urn:eu.emsa.ssn"> 
[...] 
<xsd:element name="SSN_Receipt" type="ssn:SSN_ReceiptType"/> 
[...] 
<xsd:complexType name="SSN_ReceiptType"> 
    <xsd:annotation> 
     <xsd:documentation xml:lang="en"/> 
    </xsd:annotation> 
    <xsd:sequence> 
     <xsd:element name="Header" type="ssn:Header1Type"/> 
    </xsd:sequence> 
</xsd:complexType> 
+2

请注意你的语言。这是一个社区论坛。 – 2010-11-12 15:09:15

+0

删除的语言... – 2010-11-12 15:11:53

+0

xsd文件之间有什么区别? – Kell 2010-11-12 15:14:40

回答

3

为其他贫困的灵魂将来参考,这里是我想出了一个解决方案。

正如我的问题所述,我的类是从XSD生成的。我测试了我们课程的以前版本,并且它们仍然工作得很好。另外,使用相同类的SOAP服务也适用。检查跟踪日志,我看不到任何特别揭示。

但我找到了一个具体的解决方案。我添加了以下属性上我的课:

[System.Xml.Serialization.XmlRoot(Namespace = "urn:eu.emsa.ssn", 
            ElementName = "SSN_Receipt")] 

现在,我不想我的垃圾生成的类与自定义代码,所以我加了一个局部类:

[System.Xml.Serialization.XmlRoot(Namespace = "urn:eu.emsa.ssn", 
            ElementName = "SSN_Receipt")] 
public partial class SSN_ReceiptType {} 

这解决了我的问题完全。但我仍然不明白为什么这首先打破了。

如果任何人都能拿出一个很好的可测试答案来解释它为什么会坏掉,我会做出正确的答案。

谢谢你的时间家伙!这一直是一种教育体验,在一定程度上:)

+0

哇,奇怪:我期望xsd.exe在你的类上生成这个属性。那么,如果我遇到过这个问题,我必须记住这个。 – Kell 2010-11-16 09:43:18

0

我敢肯定你的XML应该读

<?xml version="1.0" encoding="UTF-8" standalone="yes"?> 
<ssn:SSN_Receipt xmlns="urn:eu.emsa.ssn"> 
    <ssn:Header StatusMessage="SomethingSomething" StatusCode="Blabla" SSNRefId="N/A" MSRefId="2674762" Version="2.0" To="NCANOHAU1" SentAt="2010-11-12T14:48:44Z" From="SSN"/> 
</ssn:SSN_Receipt> 
+0

该元素应以前缀ssn: – Kell 2010-11-12 15:54:13

+0

为前提,谢谢,请立即尝试一下 – andrerav 2010-11-12 15:55:21

+0

修改过的XML现在产生如下结果:'ssn'是一个未声明的名称空间。第1行,第57位。 – andrerav 2010-11-12 15:56:52

0

你应该已经产生了SSN_Receipt类。将它传递给反序列化方法时,您需要使用该类。

IE:

Deserialize<SSN_Receipt>(xmlGoesHere); 

,而不是SSN_ReceiptType

+0

我不太确定 - 如果你看看XSD,生成的代码是有道理的。元素名称是SSN_Receipt,但类型名称是SSN_ReceiptType。 – andrerav 2010-11-15 09:30:44