如何在Xamarin.Forms项目中使用.netstandard的WCF服务?

6
我已经创建了一个使用 .NET Standard 2.0 作为 PCL 项目的 Xamarin.Forms 项目。我正在尝试在该项目中使用 WCF 服务。我已经添加了 WCF 服务的连接服务。但是,当我尝试调用提供的任何方法时,它会给出以下错误:

System.ServiceModel.FaultException`1[[System.ServiceModel.ExceptionDetail, System.ServiceModel, Version=2.0.5.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35]]: Error in deserializing body of request message for operation 'GetData'. OperationFormatter encountered an invalid Message body. Expected to find node type 'Element' with name 'GetData' and namespace 'http://tempuri.org/'. Found node type 'Element' with name 'GetDataAsync' and namespace 'http://tempuri.org/'

我还尝试将 .NET Standard 版本更改为旧版本,但仍然出现相同的错误。

错误提示表明身体的形状不正确,而不是方法未实现。模型是否正确? - Neil
@Neil 是的,模型是正确的。实际上,GetData方法可能存在问题,这是由于Visual Studio中WCF服务提供程序生成的代理类引起的。 - vishgarg
大家好!有人知道Xamarin是否与基于任务的异步WCF代理方法兼容吗?先谢谢了。 - Ignacio
@Ignacio 我认为这需要时间,因为目前还没有关于它实施的消息。 - vishgarg
2个回答

7

目前,Xamarin应用程序与WCF Web服务参考生成的用于.NET Standard项目的基于任务的异步WCF代理方法不兼容(bugzilla.xamarin.com Bug 51959)。

生成旧版兼容样式的WCF代理方法的一种方法是在Developer Command Prompt中运行SvcUtil.exe并使用/async/tcv:Version35开关。这将生成同步代理方法、Begin/End风格的异步编程模型(APM)回调代理方法和基于事件的代理方法,所有这些方法都与Xamarin应用程序兼容。

(注意:如果省略/async开关,则SvcUtil.exe将生成较新、不兼容的基于任务的代理方法。)


我认为,使用旧选项生成代理类的选项已经不存在了,因为Visual Studio 2017的svcutil.exe会再次生成async/await风格的代理方法。 - vishgarg
嗯。您可以尝试显式传递/tcv:Version35选项。根据文档:“使用/tcv:Version35/async开关时,将生成基于事件和回调/委托的异步方法。”在我的快速测试中,使用C:\Program Files (x86)\Microsoft SDKs\Windows\v10.0A\bin\NETFX 4.6.1 Tools\SvcUtil.exe,我得到了所需的回调和基于事件的方法。 - Brendan Zagaeski
1
啊哈。看起来如果你不加上/async标志,它现在默认会包括基于任务的方法和同步方法。我会稍微编辑一下我的答案来解决这个问题,并提到/tcv:Version35标志,因为这是获取基于事件的方法所必需的。 - Brendan Zagaeski
@BrendanZagaeski 我刚使用 svcutil 生成了一个 Reference.cs 文件并将其添加到我的 .Net Standard 1.4 项目中,但是出现了错误:“在命名空间 'System.Runtime.Serialization' 中找不到类型或命名空间名为 'IExtensibleDataObject' 的名称”。你有什么想法是什么导致了这个问题吗?我已经在网上搜索了那个参考资料但没有看到。 - JKennedy
看起来类型 IExtensibleDataObject 在 .NET Standard 1.4 中不可用。如果切换到 .NET Standard 2.0,则该类型可用,如果这对您是一个选项的话。 "WCF Web Service Reference" 代理似乎会丢弃使用该类型的属性,因此另一个选择可能是从 SvcUtil 代理中编辑受影响的属性。 - Brendan Zagaeski

3

在“配置WCF Web服务引用”界面中勾选“生成同步操作”复选框,以生成旧版本兼容的WCF代理方法:

生成同步操作

消费Web服务:

KimlikServiceReference.KPSPublicSoapClient soapClient = new KimlikServiceReference.KPSPublicSoapClient(KimlikServiceReference.KPSPublicSoapClient.EndpointConfiguration.KPSPublicSoap);
//KimlikServiceReference.TCKimlikNoDogrulaResponse response = soapClient.TCKimlikNoDogrulaAsync(TCKimlikNo, Ad, Soyad, DogumYili).Result;
bool result = soapClient.TCKimlikNoDogrula(TCKimlikNo, Ad, Soyad, DogumYili);

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接