2013-04-01 31 views
4

阅读之后Best Practices in Asynchronous Programming 我决定测试MVC4中的死锁行为。来自Intranet模板创建的网站后,我修改了索引操作是这样的:如何监视MVC4中的异步/等待死锁?

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Threading.Tasks; 
using System.Web; 
using System.Web.Mvc; 

namespace AsyncAwait.MVC4.Controllers 
{ 
    public class HomeController : Controller 
    { 
     private static async Task DelayAsync() 
     { 
      await Task.Delay(1000); 
     } 

     // This method causes a deadlock when called in a GUI or ASP.NET context. 
     public static void Test() 
     { 
      // Start the delay. 
      var delayTask = DelayAsync(); 
      // Wait for the delay to complete. 
      delayTask.Wait(); 
     } 

     public ActionResult Index() 
     { 
      ViewBag.Message = "Modify this template to jump-start your ASP.NET MVC application."; 

      Test(); 

      return View(); 
     } 
    } 
} 

到指数的调用如我所料,但我也期待一个例外,在某些时候被抛出挂起。异常不会被抛出,所有请求都会挂起。

我查看了所有可用的性能计数器,但无法弄清楚如何识别死锁。如果我要与使用异步/等待的现有网站合作,如何设置潜在的死锁监控?

谢谢!

+2

为什么你会期望死锁抛出异常? – svick

+0

@svick:你是对的,我不应该期待一个例外,误读我引用的文章。不过,我想知道是否有可能以某种方式监控死锁。谢谢! –

+1

伟大的问题。我认为这更多地涉及多线程,而不是直接与异步/等待设施相关。我认为你唯一的选择是设计某种形式的监控。我不知道使用C#或运行时的自动行为。 –

回答

0

如果您希望在可预测的时间范围内完成任务,那么您可以使用超时。

Task.Wait有几个重载需要超时值。

例如,如果你的任务不应该超过5秒钟,你可以做这样的事情。

var delayTask = DelayAsync(); 

// Will be true if DelayAsync() completes within 5 seconds, otherwise false. 
bool callCompleted = delayTask.Wait(TimeSpan.FromSeconds(5)); 

if (!callCompleted) 
{ 
    throw new TimeoutException("Task not completed within expected time."); 
} 
+0

谢谢!这绝对是其中一种方法。不过,我希望看到在修复任何代码之前,是否有可能在现有应用程序中观察到死锁。 –