我正在使用调用Web服务并在客户端上使用WCF生成的服务引用。我已经保存了从测试服务接收到磁盘的XML响应(没有SOAP信封和正文标记)我想从磁盘加载它们并从它们创建对象。让我们从我的网络服务中采取以下方法:
SomeMethodResponse SomeMethod(SomeMethodRequest req)
我手动(通过SOAP UI)将响应保存到磁盘到文件,Sample response:
<SomeMethodResponse xmlns="http://myNamespace">
<SomeMember1>value</SomeMember1>
</SomeMethodResponse>
然后我尝试使用以下命令从文件反序列化对象:
DataContractSerializer dcs =
new DataContractSerializer(typeof(SomeMethodResponse))
这失败了 - 序列化程序抱怨错误,它期望命名空间“http://schemas.datacontract.org/2004/07”中的元素,但在“http://myNamespace”中找到了元素。
问题:为什么DataContractSerializer
不使用在SomeMethodResponseType上使用XmlTypeAttribute(Namespace="http://myNamespace")
声明的命名空间?
我可以通过向DataContractSerializer
构造函数显式提供名称空间和根元素来解决这个问题。但随后失败的消息类似于:
行X位置Y(XMLdocument的最后一行)出错。 'EndElement''SomeMethodResponse
来自命名空间'httpmyNapespace'不是预期的。
期待元素'someNameField'。
SomeName
是Web服务正在使用的XSD中的一个元素。它也是SomeMethodResponse
类型的属性,由名为someNameField
的私有字段支持。看起来DataContractSerializer
除了属性之外还试图反序列化字段。
如何取消我从磁盘保存的XML并取回SomeMethod返回的相同类型的对象?
谢谢, 马特拉
答案 0 :(得分:5)
您的XML响应显然具有XML命名空间:
<SomeMethodResponse xmlns="http://myNamespace">
<SomeMember1>value</SomeMember1>
</SomeMethodResponse xmlns="http://myNamespace">
所以为了正确读取和反序列化,你需要告诉你的DataContractSerializer关于这个命名空间:
DataContractSerializer dcs =
new DataContractSerializer(typeof(SomeMethodResponse),
"SomeMethodResponse", "http://myNamespace")
通过在构造函数中指定此默认XML命名空间,它应该能够立即读取和反序列化此XML。
你得到的另一个错误:
行X位置Y(XMLdocument的最后一行)出错。 “结束元素” 不期望来自命名空间'httpmyNapespace'的SomeMethodResponse。 期待元素'someNameField'。
是由非常不寻常且前所未见的事实引起的,你的end元素上有一个命名空间........
</SomeMethodResponse xmlns="http://myNamespace">
只需删除那个额外不必要的命名空间,你应该没问题!
</SomeMethodResponse>
答案 1 :(得分:5)
让我回答一下我自己的问题:第二个错误信息的原因是,实际上,svcUtil已经默默选择使用XmlSerializer
DataContractSerializer
。我通过阅读XmlTypeAttribute
的帮助找到了这一点 - MSDn状态控制XmlSerializer序列化属性目标时生成的XML模式。 ;-)所以我们回来了到旧,XmlSerializer