我正在开发一个ASP.NET MVC WebApi项目,其中一种方法需要进行LDAP搜索。搜索从LDAP服务器检索到的信息量可确保呼叫至少花费7秒钟才能完成。由于使用System.DirectoryServices.Protocols
类和方法,因此该调用是同步的且不可修改。
此API接收的流量非常大(即使该API位于内部网络中),因此对LDAP服务器的每次调用都需要7秒。所以我想知道这一点:
await Task.Run(() => Search(params))
可以接受吗?)答案 0 :(得分:4)
如评论中所述,我完全看不到使调用异步将如何有所帮助。在另一个线程中运行它并等待(按照您的“什么是正确的方法……”问题)确实消耗了与同步调用和等待一样多的资源。
但是请注意,System.DirectoryServices.Protocols
之类的LdapCollection
类确实具有较旧的APM(异步编程模型)样式(例如BeginSendRequest
/ EndSendRequest
)的异步支持
您可以使用TaskFactory<TResult>.FromAsync
轻松地将APM样式的API包装为可等待的基于任务的样式,这是将这些类与async一起使用的“正确方法”。另请参见Interop with Other Asynchronous Patterns and Types。
答案 1 :(得分:0)
PD:根据Lucero的回答,这是一种扩展方法,该方法隐藏APM调用并将其自身公开为常规Task<T>
异步方法:
public static async Task<DirectoryResponse> SendRequestAsync(this LdapConnection conn, string target, string filter,
SearchScope searchScope, params string[] attributeList)
{
if (conn == null)
{
throw new NullReferenceException();
}
var search_request = new SearchRequest(target, filter, searchScope, attributeList);
var response = await Task<DirectoryResponse>.Factory.FromAsync(
conn.BeginSendRequest,
(iar) => conn.EndSendRequest(iar),
search_request,
PartialResultProcessing.NoPartialResultSupport,
null);
return response;
}
这也可以用作您自己需要的起点(您可以使用类似的方法来“使”支持APM的对象以基于任务的样式运行)。