WCF 服务对象序列化

本文关键字:序列化 对象 服务 WCF | 更新日期: 2023-09-27 18:34:17

我有一个名为contact的抽象类和另一个名为client的类,它继承自contact。我正在使用一种采用 contact 类型参数的方法处理 WCF 服务。但是我拥有的是我想传递的客户端实例。我面临此错误:

不需要使用数据协定名称"Client:http://schemas.datacontract.org/2004/07/xxx"键入"xxx.Client"。将静态未知的任何类型添加到已知类型列表中 - 例如,通过使用 KnownTypeAttribute 属性或将它们添加到传递给 DataContractSerializer 的已知类型列表中。

WCF 服务对象序列化

你想知道Client是一种Contact

有几种方法可以做到这一点,但它们都围绕着使用 KnownType 属性或ServiceKnownType属性。

可以将KnownType放在Client类上,以告诉 DataContractSerializer 它是 KnownType 的Contact

[DataContract]
[KnownType(typeof(Client))]
public class Contact{}

也可以将KnownType放在类上,以指示在序列化此类时也可能遇到其他类。

如果你有一个DataContract类,该类的属性是一个实际上可能包含ClientContact,则可能需要这样做:

[DataContract]
[KnownType(typeof(Client))]
public class Meeting
{
    Contact MeetingContact{get;}
}

在这种情况下,您可以在不指定客户端上指定 KnownType 的情况下逃脱。 如果您有一个返回集合的属性,并且您想要指定集合中可以存在的类型,则可能还需要执行此操作。

您可以指定静态

方法的名称,而不是指定 KnownType 的实际类型,该方法将返回已知类型:

[DataContract]
[KnownType("GetKnownTypes")]
public class Meeting
{
    Contact MeetingContact{get;}
    private static Type[] GetKnownType()
    {
    return new Type[]{typeof(Client)};
    }
}

您还可以通过配置文件指定已知类型。

ServiceKnownTypes 的工作方式类似,但在服务本身上指定:

[ServiceKnownType(typeof(Client))]
[ServiceContract()]
public interface IMyServiceContract
{
    [OperationContract]
    Contact GetContact();
}

此设置将使 DataContactSerializer 知道任何方法都可能返回类型 Client 的类型。 与已知类型类似,您还可以使用静态方法来提供服务的已知类型。

WCF 不直接用于抽象类。您应该在数据协定或服务类上使用 KnownType 属性。 以下是示例;

[DataContract]
[KnownType(typeof(Client))]
public class Contact
{
   ...
}
[ServiceContract]
[ServiceKnownType(typeof(Client))]
public interface IMyService
{
    contact getcontact(Guid id);
}
使用 [KnownType]

和 [ServiceKnownType] 属性来确保关系。