我正在尝试创建一个接受任何输入(Action =“*”)的wcf服务,然后在确定其类型后反序列化该消息。出于测试反序列化的目的,我目前正在对测试服务的类型进行硬编码。
我没有从反序列化过程中得到任何错误,但是在反序列化发生后只填充了外部对象。所有内部字段均为空。我可以成功处理与原始wcf服务相同的请求。
我正在反序列化这种方式,其中knownTypes是预期类型的类型列表:
DataContractSerializer ser = new DataContractSerializer(new createEligibilityRuleSet ().GetType(), knownTypes);
createEligibilityRuleSet newReq = buf.CreateMessage().GetBody<createEligibilityRuleSet>(ser);
这是请求对象的类和子类。这些类是由svcutil使用现有wsdl的自顶向下方法生成的。我尝试用DataContracts替换XmlTypeAttributes,用DataMembers替换XmlElements没有区别。它是createEligibilityRuleSet对象上的CreateEligibilityRuleSetSvcRequest实例,为null。我在底部包含了从请求中检索到的请求
/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("svcutil", "3.0.4506.2152")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(AnonymousType = true, Namespace = "http://RulesEngineServicesLibrary/RulesEngineServices")]
public partial class createEligibilityRuleSet
{
private CreateEligibilityRuleSetSvcRequest requestField;
/// <remarks/>
[System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified, IsNullable = true, Order = 0)]
public CreateEligibilityRuleSetSvcRequest request
{
get
{
return this.requestField;
}
set
{
this.requestField = value;
}
}
}
/// <remarks/>
[System.CodeDom.Compiler.GeneratedCodeAttribute("svcutil", "3.0.4506.2152")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(Namespace = "http://RulesEngineServicesLibrary")]
public partial class CreateEligibilityRuleSetSvcRequest : RulesEngineServicesSvcRequest
{
private string requestField;
/// <remarks/>
[System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified, Order = 0)]
public string request
{
get
{
return this.requestField;
}
set
{
this.requestField = value;
}
}
}
[System.Xml.Serialization.XmlIncludeAttribute(typeof(CreateEligibilityRuleSetSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(ApplyMemberEligibilitySvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(CreateCompletionCriteriaRuleSetSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(CopyRuleSetSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(DeleteRuleSetByIDSvcRequest))]
[System.CodeDom.Compiler.GeneratedCodeAttribute("svcutil", "3.0.4506.2152")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(Namespace = "http://RulesEngineServicesLibrary")]
public partial class RulesEngineServicesSvcRequest : ServiceRequest
{
}
/// <remarks/>
[System.Xml.Serialization.XmlIncludeAttribute(typeof(RulesEngineServicesSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(CreateEligibilityRuleSetSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(ApplyMemberEligibilitySvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(CreateCompletionCriteriaRuleSetSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(CopyRuleSetSvcRequest))]
[System.Xml.Serialization.XmlIncludeAttribute(typeof(DeleteRuleSetByIDSvcRequest))]
[System.CodeDom.Compiler.GeneratedCodeAttribute("svcutil", "3.0.4506.2152")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(Namespace = "http://FELibrary")]
public partial class ServiceRequest
{
private string applicationIdField;
/// <remarks/>
[System.Xml.Serialization.XmlElementAttribute(Form = System.Xml.Schema.XmlSchemaForm.Unqualified, Order = 0)]
public string applicationId
{
get
{
return this.applicationIdField;
}
set
{
this.applicationIdField = value;
}
}
}
来自客户的请求来自消息正文,如下所示。在运行时从消息中检索。
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope" xmlns:rul="http://RulesEngineServicesLibrary/RulesEngineServices">
<soap:Header/>
<soap:Body>
<rul:createEligibilityRuleSet>
<request>
<applicationId>test</applicationId>
<request>Perf Rule Set1</request>
</request>
</rul:createEligibilityRuleSet>
</soap:Body>
</soap:Envelope>
答案 0 :(得分:2)
您看到的具体问题是DataContract不知道如何处理不合格的元素。但是XmlSerializer可以,并且你的类被正确地归因于XmlSerializer。
因此,您应该使用XmlSerializer而不是DataContractSerializer来反序列化正文内容:
public static T GetBodyWithXmlSerializer<T>(this Message msg)
{
var ser = new XmlSerializer(typeof(T));
T o;
using (var reader = msg.GetReaderAtBodyContents())
{
o = (T)ser.Deserialize(reader);
}
return o;
}