我有一个WCF服务,它返回一个实现IExtensibleDataObject的类.我需要在这个类中添加一个新字段.我更新了DataContract接口并对类进行了更改.现在,当我尝试运行我的客户端应用程序时,我收到以下错误:
无法加载文件或程序集'xxx.yyyy.zzzz,Version = 1.3.9.26111,Culture = neutral,PublicKeyToken = b09e2f3e9b5894f0'或其依赖项之一.定位的程序集的清单定义与程序集引用不匹配.(HRESULT异常:0x80131040)
WFC类的AssemblyVersion已被更改 - 这会破坏客户端吗?
编辑:
生产中有客户使用此服务.如果可能的话,我不想让他们更新他们的服务参考并重新部署他们的客户端以进行这个简单的更改.
mar*_*c_s 26
这取决于您如何设置数据合同.
在WCF中,使用所有默认值,您的服务将使用DataContractSerializer(DCS)将对象序列化为XML.DCS将按顺序序列化您的字段 - 首先是公共字段,然后是私有字段.在每个可见性组中,它将按名称的字母顺序对字段/属性进行排序.
因此,如果你介绍一个新的公共财产MiddleName,你已经有了FirstName和LastName,你会被罚款:老XML本来
<YourObject>
....
<FirstName>.....</FirstName>
<LastName>.....</LastName>
</YourObject>
Run Code Online (Sandbox Code Playgroud)
而你的新人只需在最后添加一个新的属性:
<YourObject>
....
<FirstName>.....</FirstName>
<LastName>.....</LastName>
<MiddleName>....</MiddleName>
</YourObject>
Run Code Online (Sandbox Code Playgroud)
这样的更新"在末尾添加一些东西"应该可以正常工作,DCS只是简单地忽略XML中的其他标签.
但是:如果你引入了一个名为的属性Gender,它将被卡在 <FirstName>和之间,<LastName>从而打破XML中数据的顺序,从而破坏数据合同 - 没有"旧"客户端能够调用你的新服务.
为了控制这一点,您可以Order=在数据合同中的数据成员上添加特定属性:
[DataContract]
public class SomeAddress
{
[DataMember(Order=0)]
public string FirstName;
[DataMember(Order=1)]
public string LastName;
}
Run Code Online (Sandbox Code Playgroud)
然后,您可以轻松添加新属性 - 只需将其添加到列表的末尾即可!
[DataContract]
public class SomeAddress
{
[DataMember(Order=0)]
public string FirstName;
[DataMember(Order=1)]
public string LastName;
[DataMember(Order=2)]
public string Gender;
}
Run Code Online (Sandbox Code Playgroud)
因此,通过在Order=数据协定上使用属性,您可以控制XML布局,并且可以对现有数据合同进行简单扩展,从而实现非破坏性更新.
有关更多背景知识和深入的专业知识,您应该阅读MSDN杂志网站上的Windows Communication Foundation中的序列化 - 强烈推荐.