意外的类型 - 序列化异常

问题描述:

我有一个WCF服务。意外的类型 - 序列化异常

正常操作会看到服务器执行一些处理,通过回调将填充的XactTaskIn对象返回给客户端。我有这个工作好。

我的问题是,当我尝试将returnData变量设置为已填充的XactException并尝试通过回调将XactTaskIn发送回客户端时,出现以下异常。

例外 - “类型 'XactException' 与 数据合同名称 'XactException:HTTP://schemas.datacontract.org/2004/07/'。 预计不会考虑使用 DataContractResolver或增加任何类型 对于已知类型的列表,例如,通过使用 KnownTypeAttribute属性或由 将它们添加到传递给DataContractSerializer的已知类型列表 ,而不是静态地知道到 列表。 (System.Runtime.Serialization.SerializationException)异常 消息=“类型 'XactException' 与 数据合同名 'XactException:HTTP://schemas.datacontract.org/2004/07/'。 预计不会考虑使用一个 DataContractResolver或添加 不是静态已知的 已知类型的列表中的任何类型 - 例如,通过使用 的KnownTypeAttribute属性或由 它们添加到传递给DataContractSerializer的已知类型 列表“, 异常类型=。 “System.Runtime.Serialization.SerializationException”

这里是XactTaskIn类

[DataContract] 
public class XactTaskIn 
{ 
    [DataMember] 
    public DateTime timeOut; 
    [DataMember] 
    public DateTime timeIn; 
    [DataMember] 
    public string name; 
    [DataMember] 
    public string responseTo; 
    [DataMember] 
    public String moduleFromName; 
    [DataMember] 
    public String moduleFromType; 
    [DataMember] 
    public String methodFromName; 
    [DataMember] 
    public object[] originalInputs; 
    [DataMember] 
    public String returnMethodToCall; 
    [DataMember] 
    public String returnModuleToCall; 
    [DataMember] 
    public object returnData; 

    public XactTaskIn(DateTime timeOut, DateTime timeIn, string name, string responseTo, String moduleFromName, String moduleFromType, String methodFromName, object[] originalInputs, String returnMethodToCall, String returnModuleToCall, object returnData) 
    { 
     this.timeOut = timeOut; 
     this.timeIn = timeIn; 
     this.name = name; 
     this.responseTo = responseTo; 
     this.moduleFromName = moduleFromName; 
     this.moduleFromType = moduleFromType; 
     this.methodFromName = methodFromName; 
     this.originalInputs = originalInputs; 
     this.returnMethodToCall = returnMethodToCall; 
     this.returnModuleToCall = returnModuleToCall; 
     this.returnData = returnData; 
    } 
} 

这里是XactException类:

[DataContract]  
public class XactException 
{ 
    [DataMember] 
    string message; 

    public XactException(string message) 
    { 
     this.message = message; 
     // Add implementation. 
    } 
} 

更新:

好了,所以从丹尼尔的评论帮助了我。

现在看起来服务器正在向客户端发送回调,但客户端正在抛出以下异常。

  • 捉住:“格式化抛出异常尝试反序列化 消息:有同时 尝试反序列化参数 http://tempuri.org/:taskIn错误的 的InnerException消息是“在 第1个位置误差960。 。元素 'http://schemas.datacontract.org/2004/07/:returnData' 包含来自类型的数据,该类型映射到 名称 'http://schemas.datacontract.org/2004/07/: XactException'。 解串器不知道 映射到此名称的任何类型。 考虑使用DataContractResolver 或添加对应于 “XactException”类型已知 类型的列表 - 例如,通过使用 KnownTypeAttribute属性或由 其添加到传递给DataContractSerializer的已知类型 列表” 。 请参阅的InnerException更多 方式“ (System.ServiceModel.Dispatcher.NetDispatcherFaultException)异常 消息=”格式化抛出异常 尝试反序列化 消息:有同时 尝试反序列化参数 错误http://tempuri.org/:taskIn。所述 的InnerException信息是“错误在 第1个位置960元 ‘http://schemas.datacontract.org/2004/07/:returnData’ 包含映射到 名称 一种类型的数据的” http: //schemas.datacontract.org/2004/07/:XactException”。 解串器不知道映射到此名称的任何类型的 。 考虑使用DataContractResolver 或添加对应于 “XactException”类型已知 类型的列表 - 例如,通过使用 KnownTypeAttribute属性或由 其添加到传递给DataContractSerializer的已知类型 列表” 。 请参阅的InnerException更多 细节。“,异常类型= ”System.ServiceModel.Dispatcher.NetDispatcherFaultException“
+0

尝试使用“KnownTypeAttribute”,如例外中详述。 – 2011-05-27 13:52:54

+1

@Daniel - 我会在哪里放置这个属性? – user589195 2011-05-27 13:54:19

+0

@ user589195:我想在'XactException'类中。 – 2011-05-27 14:04:54

在你的类

[DataContract] 
    public class XactTaskIn 

你必须返回对象的属性:

 [DataMember] 
     public object[] originalInputs; 

     [DataMember] 
     public object returnData; 

WCF需要提前什么类型的都不可能在那里知道,所以它可以告诉客户端(通过WSDL)所有类型是什么。对于任何/所有非'原生'类型(任何不是int,字符串,DateTime等),您将需要为可能在这些对象属性中传回的每种可能类型添加[KnownType]属性,如下所示:

[KnownType(typeof(XactException))] 
    [KnownType(typeof(...))] 
    [KnownType(typeof(...))] 
    [DataContract] 
    public class XactTaskIn 

WCF为服务构建WSDL时,会知道将XactException添加到数据类型列表中,并且序列化程序也知道要查找这些类。


Side-note;如果您的客户端是使用SrvUtil,Service Reference构建的,或者以某种方式从WSDL生成的,则需要在添加[KnownType]属性后重建客户端!

+2

非常好,非常感谢,帮助我理解它,而不仅仅是给我答案:) – user589195 2011-05-27 15:13:24

+0

我有更多的问题,我有一个公共领域,但只有一个get,需要一套,然后我看到下一个错误列表 – TruthOf42 2013-07-26 18:39:56

你的客户期待XactTaskIn不是XactException。

你需要改变您的XactTaskIn能够将异常对象传递回您的客户端

删除您的异常datacontract并将XactException类型作为数据成员添加到您的XactTaskIn类中

+0

嗨肯谢谢你的回答 - 我想我正在努力做你的建议。我不是试图向客户端发送XactException,而是尝试向其returnData数据元包含XactException对象的XactTaskIn对象发送消息。 – user589195 2011-05-27 14:03:21

当数据发生变化时,会发生串行化异常,例如,将字段名从awesomeString更改为awesomeSTring会导致序列化中断。原因是新数据不能再根据旧数据进行验证。此修复程序使用服务器/客户端期望的旧版本。