使用与WCF的接口

我已经谷歌搜索并阅读了几个小时,我找不到任何处理我特定情况的人…

我想在我的WCF服务合同中使用接口来松散地将服务从线路每端使用的类中耦合出来。 这将使我们能够拥有一个低级程序集,其中只包含我们可以提供给顾问的服务和数据合同(只是接口)。 在他们的结束时,他们可以实例化他们的数据类,实现我们的数据合同接口,通过网络将它发送给我们,然后我们的WCF服务将转换/转换/任何传入的数据到我们的实现的数据类的版本相同的界面。

这是一个例子。 IDataContract包含我想通过网络传输的裸信息。 端点和其他特定于WCF的配置都是默认的东西(我的问题可能在于,所以如果我需要更改内容,我可以包含更多内容)。

编辑 :我已经包含了更多的代码,并重命名了几个类,以帮助它减少混乱。 DataContractAttributes的名称和命名空间添加,以及配置文件中的两个部分是基于此博客文章中的信息的新增内容。 如果我切换到抽象基类而不是接口, 它就可以工作 但是,如果可能的话,我想使用接口。

共享库(我的代码,与客户作者共享):

 public interface IDataContract { string MyProperty { get; set; } } [ServiceContract] public interface ITestService { [OperationContract] IDataContract TestSharedInterface(IDataContract clientData); } 

客户代码(他们的):

 [DataContract(Name = "IDataContract", Namespace = "http://services.sliderhouserules.com")] public class ClientDataClass : IDataContract { [DataMember] public string MyProperty { get; set; } } private static void CallTestSharedInterface() { EndpointAddress address = new EndpointAddress("http://localhost/ServiceContractsTest.WcfService/TestService.svc"); ChannelFactory factory = new ChannelFactory("ITestService", address); ITestService proxy = factory.CreateChannel(); ((IClientChannel)proxy).Open(); IDataContract clientData = new ClientDataClass() { MyProperty = "client data" }; IDataContract serverData = proxy.TestSharedInterface(clientData); MessageBox.Show(serverData.MyProperty); } 

客户端配置:

          

服务器代码(我的):

 public class TestService : ITestService { public IDataContract TestSharedInterface(IDataContract clientData) { ServerDataClass convertedClientData = (ServerDataClass)clientData; IDataContract serverData = new ServerDataClass() { MyProperty = convertedClientData.MyProperty + " + server data added" }; return serverData; } } [DataContract(Name = "IDataContract", Namespace = "http://services.sliderhouserules.com")] public class ServerDataClass : IDataContract { [DataMember] public string MyProperty { get; set; } } 

服务器配置:

          

我在客户端调用上收到序列化错误抱怨已知类型。 我刚刚在该客户端类中缺少一些元数据标记吗? 我甚至不知道哪里甚至可以知道这个问题,因为我已经尝试了所有我能想到的搜索,似乎没有人能够处理这个具体的情况。

基本上,我希望ClientDataClass序列化为client data ,然后能够将其反序列化为ServerDataClass实例。 这似乎应该是可能的。

如果您的数据协定是接口,则WCF无法知道要为传入请求实例化的对象。 在所有Add Service Reference读取WSDL并根据WSDL中的类型信息生成新类之后,不需要该类与服务中的相同。

这个博客为我提供了找到问题解决方案的正确方向。 实际上我在他的post中有类似sliderhouserules描述的完全相同的场景。

但在我的场景中,我不能使用任何抽象或基类来inheritance。 所以我使用了TypesHelper类来自己读取dataContractSerializer部分,并将相关类型传递给WCF服务。

 namespace ExampleNamespace { public interface IJustAInstance { } [ServiceContract] [ServiceKnownType("GetKnownTypes", typeof(ExampleNamespace.TypesHelper))] public interface ICreateInstance { IJustAInstance CreateInstance(); } public static class TypesHelper { public static IEnumerable GetKnownTypes(ICustomAttributeProvider provider) { DataContractSerializerSection section = (DataContractSerializerSection) ConfigurationManager.GetSection( "system.runtime.serialization/dataContractSerializer"); if (dataContractSerializerSection != null) { foreach (DeclaredTypeElement item in dataContractSerializerSection.DeclaredTypes) { foreach (TypeElement innterItem in item.KnownTypes) { Type type = Type.GetType(innterItem.Type); if (typeof(IJustAInstance).IsAssignableFrom(type )) yield return type; } } } } } } 

您可以创建ClientContract和ServerContract可以提供的BaseContract(作为属性),并且可以在创建ClientContract或ServerContract的新实例时在相应的构造函数中使用。 然后,您只需将BaseContract添加到共享库中。