代码之家  ›  专栏  ›  技术社区  ›  JuChom

如何使用async/await处理潜在的大量任务?

  •  1
  • JuChom  · 技术社区  · 6 年前

    我有一个Azure函数,它可以用Dapper查询数据库,有时会引发以下异常:

    • 系统InvalidOperationException:操作无效。连接已关闭。

    • 系统InvalidOperationException:由于连接已断开,无法完成请求的操作。

    下面是我的代码所做的:

    using (var conn = new SqlConnection(_dbConnectionString))
    {
          await conn.OpenAsync();
          List<Guid> ids = await conn.QueryAsync<Guid>("SELECT Id From Table1;");
    
          var tasksRelations = ids.Select(id => conn.QueryAsync<CsvExport>(
                                          @"SELECT Field1, Field2, ... Field25 
                                            FROM Table2 
                                            WHERE Table1Id = @Id;", 
                                           new { id }));
    
          var relations = await Task.WhenAll(tasksRelations);
    }
    

    当ID数量较低时,这很好,但当ID越来越大时,我有上述例外。

    您有什么想法或方法可以让这段代码更加健壮吗?

    1 回复  |  直到 6 年前
        1
  •  2
  •   Damien_The_Unbeliever    6 年前

    您试图同时对同一连接发出多个查询。这是一个坏主意,可能有一个您在这里没有报告的初始错误,表示不支持在同一个连接上打开多个结果集。

    而不是运行这么多查询, 简化 您的代码可以在 仅有一个的 查询:

    using (var conn = new SqlConnection(_dbConnectionString))
    {
          await conn.OpenAsync();
          var relations = conn.QueryAsync<CsvExport>(
                                          @"SELECT Field1, Field2, ... Field25 
                                            FROM Table2 
                                            WHERE Table1Id IN (SELECT Id From Table1);");
    }
    

    现在,您不必处理“大量”任务,只需在连接上运行一个查询,因此不应生成错误。