Dot*_*mer 3 .net c# asp.net asp.net-mvc async-await
我返回一个基本上调用两个异步操作的列表:
[HttpPost]
public ActionResult List(DataSourceRequest command, ProductListModel model)
{
var categories = _productService.GetAllProducts(model.SearchProductName,
command.Page - 1, command.PageSize);
var gridModel = new DataSourceResult
{
Data = categories.Select(async x =>
{
var productModel = x.ToModel();
var manufacturer = await _manufacturerService.GetManufacturerById(x.ManufacturerId);
var category = await _categoryService.GetCategoryById(x.CategoryId);
productModel.Category = category.Name;
productModel.Manufacturer = manufacturer.Name;
return productModel;
}),
Total = categories.TotalCount
};
return Json(gridModel);
}
Run Code Online (Sandbox Code Playgroud)
这是一个ajax请求(来自客户端),但在前端它永远不会返回.有没有僵局?
从几条评论和@ usr的答案中建立我的答案:
Data在上面的代码实际上IEnumerable<Task<ProductModel>>,不是IEnumerable<ProductModel>.这是因为拉姆达传递到Select是async.Task<ProductModel>实例上的属性,包括Result.我在我的博客上解释为什么Result在这种情况下访问会导致死锁.简而言之,这是因为asynclambda将尝试在ASP.NET请求上下文之后继续执行await.但是,ASP.NET请求上下文在调用时被阻止Result,锁定该请求上下文中的线程直到Task<T>完成.由于asynclambda无法恢复,因此无法完成该任务.所以这两件事情都在相互等待,你会遇到经典的僵局.
有一些建议可供使用await Task.WhenAll,我通常会同意这些建议.但是,在这种情况下,您正在使用Entity Framework并出现此错误:
在先前的异步操作完成之前,在该上下文上开始第二操作.
这是因为EF不能在同一个db上下文中同时执行多个异步调用.有几种方法可以解决这个问题; 一种是使用多个db上下文(实质上是多个连接)来同时进行调用.IMO更简单的方法是顺序进行异步调用而不是并发:
[HttpPost]
public async Task<ActionResult> List(DataSourceRequest command, ProductListModel model)
{
var categories = _productService.GetAllProducts(model.SearchProductName,
command.Page - 1, command.PageSize);
var data = new List<ProductModel>();
foreach (var x in categories)
{
var productModel = x.ToModel();
var manufacturer = await _manufacturerService.GetManufacturerById(x.ManufacturerId);
var category = await _categoryService.GetCategoryById(x.CategoryId);
productModel.Category = category.Name;
productModel.Manufacturer = manufacturer.Name;
data.Add(productModel);
}
var gridModel = new DataSourceResult
{
Data = data,
Total = categories.TotalCount
};
return Json(gridModel);
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1150 次 |
| 最近记录: |