cacheItemPolicy.UpdateCallback事件和其他事件委托上的async / await

时间:2015-05-20 19:39:39

标签: c# asp.net asynchronous async-await task-parallel-library

操作方法:从委托void事件方法调用await方法?

将(ASP.NET)应用程序转换为异步是一种全部授权。但是那些不受支持的地方呢?

var policy = new CacheItemPolicy();
policy.UpdateCallback = CacheEntryUpdateCallback;

void VoidDelegate(CacheEntryUpdateArguments arguments) {
   // need this - but no can't do :(
   await SomeApi.AsyncOnlyMethodAsync(); 
}

等待是不允许的,那该怎么办? 正确这样做的方法是什么?这个问题也适用于像myButton.Commmand += new CommandEventHandler(VoidDelegate)

这样的WebForms上的事件处理程序

A:

void VoidDelegate(CacheEntryUpdateArguments arguments) {
   Task.Factory.StartNew(new Func<Task>(async () => {
     await SomeApi.AsyncOnlyMethodAsync();
   })).Unwrap().Wait();
}

这会起作用,但会转向另一个线程吗?至少它不会使该线程可用于池,并且此处异步的目的已消失。

或者支持 B:

async void VoidDelegate(CacheEntryUpdateArguments arguments) {
  await SomeApi.AsyncOnlyMethodAsync();
}

但这是一次“忘不了” - 但缓存更新事件需要在返回结果之前获取新数据。同样适用于例如按钮命令事件 - 页面可以在命令完成之前完成。

1 个答案:

答案 0 :(得分:1)

您可以将任何返回voidTaskTask<T>的方法标记为async。将方法标记为async并不会更改方法的签名,因此,如果您希望将VoidDelegate标记为async,则可以将其标记为await async void事情。

请注意,由于您现在拥有from distutils.core import setup from Cython.Build import cythonize setup(ext_modules = cythonize("myfile.pyx")) 方法,因此这将是一种即发即弃的方法。当有人调用委托时,该方法将很快返回,同时异步工作继续发生,并且调用者无法知道工作何时完成,或者是否错误。