use*_*195 48 .net c# wcf serialization exception-handling
我有一个WCF服务.
正常操作会看到服务器正在进行一些处理,通过回调将填充的XactTaskIn对象返回给客户端.我有这个工作正常.
我的问题是,当我尝试将returnData变量设置为填充的XactException并尝试通过回调将XactTaskIn发送回客户端时,我会抛出以下异常.
异常 - 不要求"数据协定名称为'XactException:http://schemas.datacontract.org/2004/07/'的类型'XactException'.请考虑使用DataContractResolver或将已知类型静态未知的任何类型添加到已知类型列表中 - 例如,通过使用KnownTypeAttribute属性或将它们添加到传递给DataContractSerializer的已知类型列表中." (System.Runtime.Serialization.SerializationException)异常消息="类型'XactException',数据协定名称为'XactException:http://schemas.datacontract.org/2004/07/'不是预期的.考虑使用DataContractResolver或添加任何静态地知道已知类型列表的类型 - 例如,通过使用KnownTypeAttribute属性或将它们添加到传递给DataContractSerializer的已知类型列表.",Exception Type ="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;
}
}
Run Code Online (Sandbox Code Playgroud)
这是XactException类:
[DataContract]
public class XactException
{
[DataMember]
string message;
public XactException(string message)
{
this.message = message;
// Add implementation.
}
}
Run Code Online (Sandbox Code Playgroud)
更新:
好的,丹尼尔的评论帮助了我.
它现在看起来像服务器正在向客户端发送回调,但客户端抛出以下异常.
- 抓住:"格式化程序在尝试反序列化消息时抛出异常:尝试反序列化参数 http://tempuri.org/:taskIn时出错.InstallException消息是'第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时出错 .InstallException消息是'第1行位置错误960.元素'http://schemas.datacontract.org/2004/07/:returnData'包含映射到名称'http://schemas.datacontract.org/2004/07的类型的数据/:XactException'.反序列化器不知道任何映射到此名称的类型.考虑使用DataContractResolver或将与"XactException"对应的类型添加到已知类型列表中 - 例如,通过使用KnownTypeAttribute属性或通过添加它到传递给DataContractSerializer的已知类型列表.'.请参阅InnerException以获取更多详细信息.",Exception Type ="System.ServiceModel.Dispatcher.NetDispatcherFaultException"
Cod*_*ike 80
在你的班上
[DataContract]
public class XactTaskIn
Run Code Online (Sandbox Code Playgroud)
你有返回对象的属性:
[DataMember]
public object[] originalInputs;
[DataMember]
public object returnData;
Run Code Online (Sandbox Code Playgroud)
WCF需要提前知道可能存在哪些类型,以便它可以告诉客户端(通过WSDL)所有类型是什么.对于任何/所有非'native'类型(任何不是int,string,DateTime等),您需要为可能在这些对象属性中传回的每种可能类型添加[KnownType]属性,如下所示:
[KnownType(typeof(XactException))]
[KnownType(typeof(...))]
[KnownType(typeof(...))]
[DataContract]
public class XactTaskIn
Run Code Online (Sandbox Code Playgroud)
这样,当WCF为服务构建WSDL时,它会知道将XactException添加到数据类型列表中,并且序列化程序也知道要查找这些类.
边注; 如果您的客户端是使用SrvUtil,Service Reference构建的,或者以某种方式从WSDL生成,则需要在添加[KnownType]属性后重建客户端!