Answers:
通常,我发现这是一个代码生成问题,大多数情况下是因为我遇到无法解决的类型名称冲突。
如果右键单击服务引用,然后单击“配置”,然后取消选中 “在引用的程序集中重新使用类型”,则可能会解决该问题。
如果您正在使用此功能的某些方面,则可能需要确保清除了您的姓名。
正如公认的答案所指出的,重用类型时的类型引用问题可能是罪魁祸首。我发现当您无法轻松确定问题时,然后使用svcutil.exe命令行将帮助您揭示潜在的问题(正如John Saunders指出的那样)。
作为增强功能,这里是使用svcutil的快速示例。
svcutil /t:code https://secure.myserver.com/services/MyService.svc /d:test /r:"C:\MyCode\MyAssembly\bin\debug\MyAssembly.dll"
哪里:
完整的svcutil命令行参考在这里:http : //msdn.microsoft.com/zh-cn/library/aa347733.aspx
一旦运行svcutil,您应该看到导入引发的异常。您可能会收到有关您的一种类型的消息:“无法使用引用的类型,因为它与导入的DataContract不匹配”。
可以简单地指定这一点,因为所引用程序集中的一种类型与在DataContract中为该服务生成的类型有所不同。就我而言,我要导入的服务具有比共享程序集中的服务更新的类型。这不是很明显,因为例外中提到的类型似乎是相同的。不同的是该类型使用的嵌套复杂类型之一。
还有其他更复杂的情况,可能会触发这种类型的异常并导致空白的reference.cs。这是一个例子。
如果遇到此问题,并且没有在数据协定中使用通用类型,也没有使用IsReference = true,那么建议您确定在客户端和服务器上共享类型是否完全相同。否则,您可能会遇到此问题。
发生这种情况时,请在“错误”窗口和“输出”窗口中查看是否有任何错误消息。如果那没有帮助,请尝试svcutil.exe
手动运行,然后查看是否有任何错误消息。
这个问题困扰我整整一整天。我已经解决了。这是如何做...
该服务必须在SSL上运行(即,它位于https://mydomain.com/MyService.svc)
在开发服务器上向WCF服务添加服务引用就可以了。
在实时生产服务器上部署完全相同的WCF服务构建,然后切换到客户端应用程序,并将服务引用配置为指向实时服务,但没有显示错误,但该应用程序无法构建:事实证明,服务引用的Reference.cs文件完全为空!更新服务参考没有区别。清洁溶液无济于事。重新启动VS2010没什么区别。创建一个新的空白解决方案,启动一个控制台项目并将服务引用添加到实时服务中时,出现了完全相同的问题。
我不认为这是由于类型冲突或其他原因造成的,但是到底是什么-我通过取消选中“在所有引用的程序集中重用类型”来重新配置WCF服务引用。不高兴 我把复选标记放回去。
下一步是尝试在参考URL上使用svcutil,以查看这是否有助于发现问题。这是命令:
svcutil /t:code https://mydomain.com/MyService.svc /d:D:\test
这产生了以下内容:
Microsoft (R) Service Model Metadata Tool
[Microsoft (R) Windows (R) Communication Foundation, Version 4.0.30319.1]
Copyright (c) Microsoft Corporation. All rights reserved.
Attempting to download metadata from 'https://mydomain.com/MyService.svc' using WS-Metadata Exchange or DISCO.
Error: Cannot import wsdl:portType
Detail: An exception was thrown while running a WSDL import extension: System.ServiceModel.Description.DataContractSerializerMessageContractImporter
Error: Schema with target namespace 'http://mynamespace.com//' could not be found.
XPath to Error Source: //wsdl:definitions[@targetNamespace='http://mynamespace.com//']/wsdl:portType[@name='IMyService']
Error: Cannot import wsdl:binding
Detail: There was an error importing a wsdl:portType that the wsdl:binding is dependent on.
XPath to wsdl:portType: //wsdl:definitions[@targetNamespace='http://mynamespace.com//']/wsdl:portType[@name='IMyService']
XPath to Error Source: //wsdl:definitions[@targetNamespace='http://tempuri.org/']/wsdl:binding[@name='WSHttpBinding_IMyService']
Error: Cannot import wsdl:port
Detail: There was an error importing a wsdl:binding that the wsdl:port is dependent on.
XPath to wsdl:binding: //wsdl:definitions[@targetNamespace='http://tempuri.org/']/wsdl:binding[@name='WSHttpBinding_IMyService']
XPath to Error Source: //wsdl:definitions[@targetNamespace='http://tempuri.org/']/wsdl:service[@name='MyService']/wsdl:port[@name='WSHttpBinding_IMyService']
Generating files...
Warning: No code was generated.
If you were trying to generate a client, this could be because the metadata documents did not contain any valid contracts or services
or because all contracts/services were discovered to exist in /reference assemblies. Verify that you passed all the metadata documents to the tool.
Warning: If you would like to generate data contracts from schemas make sure to use the /dataContractOnly option.
那让我完全难住了。尽管进行了繁琐的搜索,并且变得相当偏颇,并且重新考虑了作为公交车司机的职业,但我终于考虑了为什么它在开发箱上可以正常工作。可能是IIS配置问题吗?
我同时远程进入开发和实时框,并在每一个上启动IIS管理器(运行IIS 7.5)。接下来,我检查了每个框上的每个配置设置,比较了每个服务器上的值。
并存在问题:在站点的“ SSL设置”下,确保已选中“需要SSL”,然后选中“客户端证书”单选按钮以选择“接受”。问题已解决!
我从先前版本升级的Silverlight 5遇到了这个问题。
即使重新添加服务引用,仍然给了我一个空的Reference.cs
最后,我不得不创建一个全新的项目并重新创建服务参考。如果您在此上花费了超过半小时,可以尝试一下。即使您决定修复原始项目,您可能也想尝试一下此操作以查看发生了什么,然后向后工作以尝试解决问题。
我从未弄清楚问题出在哪里-但是.csproj文件中的某些内容可能没有升级,或者某些设置出错。
System.Xml.Linq
-如果已切换版本,请检查所有DLL的版本
如果您是最近开始在项目中添加一个集合的,则该问题可能是由两个具有相同CollectionDataContract属性的集合引起的:
[CollectionDataContract(Name="AItems", ItemName="A")]
public class CollectionA : List<A> { }
[CollectionDataContract(Name="AItems", ItemName="A")] // Wrong
public class CollectionB : List<B> { }
我通过遍历项目并确保每个Name和ItemName属性都是唯一的来解决该错误:
[CollectionDataContract(Name="AItems", ItemName="A")]
public class CollectionA : List<A> { }
[CollectionDataContract(Name="BItems", ItemName="B")] // Corrected
public class CollectionB : List<B> { }
然后,我刷新了服务参考,然后一切又恢复了。
我的问题是我将“ mex ” 留在了Web服务链接的末尾。
代替“ http://yeagertech.com/yeagerte/YeagerTechWcfService.YeagerTechWcfService.svc/mex ”
使用“ http://yeagertech.com/yeagerte/YeagerTechWcfService.YeagerTechWcfService.svc ”
在阅读了这些答案无济于事后,对我而言有效的技术只是以二进制搜索方式注释掉我的所有合同,并取消注释位,直到不再起作用。这样可以缩小令人讨厌的代码范围。
然后,您只需要猜测该代码出了什么问题。
当然,该工具中的一些错误反馈也会有所帮助。
我正在写一个Web服务合同。我有一个没有成员的占位符枚举。没关系。但是,如果我在另一个类的属性中使用它,然后在客户端上重新使用合同dll,则代码生成将爆炸而没有错误消息。运行svcutil.exe并没有帮助,只是输出了一个CS文件而未提及原因。
正如@dblood指出的那样,主要的麻烦在于DataContractSerializer,它不能正确地重用这些类型。这里已经有一些答案,因此我将在此基础上添加一些优点和缺点:
幸运的是,如果您控制服务,那么有一个简单的解决方案可以解决所有这些问题。这意味着您仍然可以跨DLL重用服务接口,这是IMO正确解决方案的必备条件。解决方案的工作方式如下:
使用相同的DLL使用您喜欢的方法构造客户端。例如(IMyInterface是服务合同接口):
var httpBinding = new BasicHttpBinding();
var identity = new DnsEndpointIdentity("");
var address = new EndpointAddress(url, identity, new AddressHeaderCollection());
var channel = new ChannelFactory<IMyInterface>(httpBinding, address);
return channel.CreateChannel();
换句话说:不要使用“添加服务引用”功能,而是通过绕过代理生成来强制WCF使用(正确)服务类型。毕竟,您已经拥有了这些课程。
专业人士:
缺点:
在双方使用项目引用时(服务项目和具有服务引用的项目),我还遇到了服务引用损坏的问题。例如,如果所引用项目的.dll被称为“ Contoso.Development.Common”,但是项目名称被简称为“ Common”,则对该项目的项目引用也被命名为“ Common”。但是,该服务需要用于解析类的“ Contoso.Development.Common”引用(如果在服务引用选项中激活了该选项)。
因此,使用资源管理器,我打开了引用服务和“ Common”项目的项目的文件夹。在那里,我用记事本编辑了VS项目文件(.csproj)。搜索引用项目的名称(在此示例中为“ Common.csproj”),您将快速找到代表项目引用的配置条目。
我变了
<ProjectReference Include="..\Common\Common.csproj">
<Project>{C90AAD45-6857-4F83-BD1D-4772ED50D44C}</Project>
<Name>Common</Name>
</ProjectReference>
至
<ProjectReference Include="..\Common\Common.csproj">
<Project>{C90AAD45-6857-4F83-BD1D-4772ED50D44C}</Project>
<Name>Contoso.Development.Common</Name>
</ProjectReference>
重要的是将引用的名称更改为引用的项目作为输出的dll的名称。
然后切换回VS。由于已在VS外部对其进行了修改,因此将要求您重新加载该项目。单击重新加载按钮。
完成此操作后,添加和更新服务参考就可以按预期进行。
希望这也可以帮助其他人。
关于MH
跟着这些步骤:
添加服务时,这些文件夹中似乎保留了一些引用,从而在自动生成代码期间导致错误。