13

我需要调用一个Task从内部返回 a 的方法

public override void OnActionExecuting(ActionExecutingContext filterContext)

它不会让我使这个方法异步它抛出以下

异步模块或处理程序已完成,而异步操作仍处于挂起状态。

和打电话的时候

 entityStorage.GetCurrentUser().Result

我陷入僵局。我怎样才能避免这种情况?

我一直在玩弄它想出类似的东西

entityStorage.GetCurrentUser().Result.ConfigureAwait(false).GetAwaiter().GetResult();

但这行不通。我该怎么做?我的解决方案需要使用 ASP.NET 4 和 Async Targetting Pack,我不能像部署到 Azure 一样使用 ASP.NET 4.5。

4

3 回答 3

13

这里解释了死锁的原因。简而言之,不要阻塞async代码。您应该ConfigureAwait(false)在您的库async代码和await结果中使用(不使用Resultor Wait)。

更新:在此处为 MVC 团队投票以添加对async操作过滤器的支持。

于 2012-08-09T17:12:45.103 回答
2

由于 await 只是编译器为您重写延续的语法糖,因此最“直接”的路径是采用将遵循您的 await 的任何代码并将其设为 ContinueWith 调用。

所以,像:

entityStorage.GetCurrentUser().ContinueWith(t =>
{
    // do your other stuff here
});
于 2012-08-09T17:54:10.050 回答
1

如果您必须将异步转换为同步。

public User GetCurrentUserSynch()
    {
        return Task.Run(() =>
        {
            var asyncResult = entityStorage.GetCurrentUser();
            while (!asyncResult.IsCompleted)
            {
                Application.Current.TryFindResource(new object()); // This is for WPF but you can do some other nonsense action of your choosing
            }

            return asyncResult.Result;
        }).Result;
    }

否则使用@Stephen 的答案。

于 2014-09-29T15:37:15.750 回答