C# 从WCF服务调用异步方法

C# 从WCF服务调用异步方法,c#,wcf,asynchronous,async-await,C#,Wcf,Asynchronous,Async Await,我想从WCF服务调用异步方法,类似于: [ServiceContract] interface IService { [OperationContract] int SomeMethod(int data); } int SomeMethod(int data) { var query = ... build LINQ query; var response = await query.ToListAsync(); return response.Len

我想从WCF服务调用异步方法,类似于:

[ServiceContract]
interface IService
{
    [OperationContract]
    int SomeMethod(int data);
}

int SomeMethod(int data)
{
    var query = ... build LINQ query;
    var response = await query.ToListAsync();
    return response.Length;
}
我不想将
async
添加到
IService
接口或
SomeMethod
方法中。使用异步方法是一个内部问题,不应该反映在接口中

我该怎么做

澄清:


我这里的问题是在非
async
方法中使用
await
。我不想更改服务契约(客户端不一定知道什么是
async
),我也不想将该方法拆分为
BeginSomeMethod
EndSomeMethod
。我想要一种在内部使用
wait
的方法。

服务器使用的是同步还是异步代码对客户端来说并不重要。客户机和服务器由指定的有线协议(通常是SOAP)分隔。SOAP没有异步完成的概念

您可以有同步服务器和异步客户端,反之亦然客户端甚至无法检测服务器是同步的还是异步的。这是一个实现细节。服务器可能是一个运行Linux的手表,但您仍然无法判断

您使用的IO样式是一个实现细节,不会影响通过网络传输的字节。

所以选择你喜欢的。客户端仍然可以使用异步IO访问服务器。

我不知道为什么这会让人们如此惊讶。在其他上下文中,这似乎非常直观:您可以有一个异步TCP服务器和一个同步客户端。我可以说
newwebclient().DownloadString(url)
,然后从以异步方式实现的web服务器同步下载字符串。我甚至不知道运行的是什么服务器软件

当您拨打WCF电话时,使用Fiddler查看线路上的内容。没有同步或异步调用的概念。

在后台,当您异步调用服务时,WCF客户端库将以异步方式使用TCP套接字。当您同步调用时,TCP套接字将与阻塞调用一起使用。这就是全部的区别

除了同步方法之外,WCF生成的客户机还可以使用异步方法。在UI中选择“生成异步操作”选项。现在两个版本都有了。两者都功能齐全

下面是如何通过一个实验让自己相信这一点:编写一个同步服务器,并从同一个.NET客户端将其同时称为sync和async。现在,异步编写第二个服务器(以您喜欢的任何样式),并使用完全相同的客户机代码来调用它


Task
IAsyncResult
无论如何都不能通过SOAP序列化,因此不可能将
Task
传输到客户端。

我认为这不符合@zmbq在以下内容中指出的目标:“根据定义,该方法是一个长时间执行的方法。不希望阻塞的客户端需要实现自己的异步机制。我希望在服务器中使用async,而不考虑客户机(例如,客户机可能正在运行.NET4,而根本不支持async/Wait)。“我想我的答案是:)他可以在服务器上使用async,不管客户端做什么。客户端可以同步调用异步服务器。无任务。需要等待或类似操作。每个生成的WCF客户端都有用于同步和异步调用的方法。两者都很好。让我这样说吧,如果API在服务器上启动了一个异步操作(称之为
SomeMethodStart
),它将如何通知客户端它的完成?它将有一个客户端代理
BeginSomeMethodStart
EndSomeMethodStart
方法,但只要服务器上返回
SomeMethodStart
调用客户端上的
EndSomeMethodStart
,就会返回,不是在服务器端异步操作结束时。他需要的是正确地向客户端公开服务器端异步操作,并且能够在服务器上使用
async/wait
,而不会阻塞。该服务需要公开APM或TAP API。当(异步)服务器完成处理时,它会发送响应。BeginXXX方法完成后不发送响应。没有一个字节。响应在服务器上完成EndXXX方法之后出现
在客户端调用EndSomeMethodStart将在服务器上返回SomeMethodStart后立即返回
否-响应到达时返回。响应在服务器完成所有处理后到达。试试看。用小提琴观察。@usr,我现在已经玩过了。我确实学到了一些新的东西,我得到了纠正,非常感谢。相关: