MVC 控制器上的异步等待,存储库选择并返回集合

本文关键字:选择 返回 集合 存储 控制器 异步 等待 MVC | 更新日期: 2023-09-27 18:31:36

我有一个MVC控制器操作,它列出了给定"应用程序"的所有"功能",然后将其显示为表格。

我在这里正确使用异步吗?

控制器操作是异步的,即

public async Task<IActionResult> List(string id)
{
  return View(await new FeatureRepository(_context).GetAllFeatures());
}

和我的功能存储库(稍后我将通过依赖注入实例化)...

public class FeatureRepository
{
  private ApplicationDbContext _context;
  public FeatureRepository(ApplicationDbContext context)
  {
    _context = context;
  }
  public async Task<IQueryable<ApplicationFeature>> GetAllFeatures()
  {
    var query = from d in _context.ApplicationFeatures
                select d;
    return query;
   }
}

或者我需要使用:

await query.ToListAsync()

然后返回一个列表? 试图避免任何类型的 ToList,因为我不想在需要之前运行查询,即延迟执行。

它似乎运行良好,但在我重现此 X 次之前,我想确保它以不同步行为的方式完成。

谢谢!担。

(MVC 6、ASP.NET 5、实体框架 7、VS2015)

MVC 控制器上的异步等待,存储库选择并返回集合

您的等待 GetAllFeatures 不会等待任何东西,因为该方法没有执行任何异步操作,只是返回一个 IQueryable。

所以你需要在某个地方调用ToListAsync。如果希望存储库返回可查询项,请从那里删除所有异步/等待,并在操作中使用 ToListAsync。

顺便说一下,请记住按照约定Microsoft的建议,使用异步后缀命名异步方法。

只是为了澄清 EF 何时公开异步,何时不公开(因为没有任何意义):

MVC 中异步操作的要点是在存在不需要 IIS 处理的操作时释放 IIS 线程。最常见和最明显的情况是数据库操作。这就是为什么大多数 MVC 异步示例都与 EF 相关,因为您可以让 IIS 在数据库处理查询时处理其他请求。

话虽如此,并且谈到 EF,只有公开异步的 EF 方法是执行数据库操作的方法。这就是为什么你没有"AddAsync"(因为Add仅适用于DbContext),而你有"SaveChangesAsync"(因为在这种情况下它实际上执行数据库插入)。

结论:若要充分利用异步操作,应使用可用的所有 EF 异步方法。如果您的操作不使用任何异步方法,则该操作不应是异步的。