首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >DbConnection.Open()可以工作,但dbConnection.OpenAsync()不能

DbConnection.Open()可以工作,但dbConnection.OpenAsync()不能
EN

Stack Overflow用户
提问于 2013-05-16 17:32:44
回答 3查看 3.7K关注 0票数 2

这是一个困难的问题。使用完全相同的查询字符串,使用完全相同的以下代码:

代码语言:javascript
复制
using (var db = new SqlConnection(queryString))
{
   await db.OpenAsync();
   var results = await db.ExecuteSomethingAsync...;
   db.Close();
{

在windows应用程序中运行时将正常工作。然而,当从IIS Express或IIS7运行时,它将永远停留在await OpenAsync()中。如果我用db.Open()替换该行,它仍然可以工作。有什么建议吗?

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2013-05-16 18:18:00

正如其他人所提到的,首先确保您的层次结构中没有WaitResult调用。async方法链在依赖于框架的入口点结束。在UI/WebForms应用程序中,这通常是一个async void事件处理程序。在WebAPI/MVC应用程序中,这通常是一个async操作。

要检查ASP.NET的另外两件事是:

  • 确保您的目标平台为.NET 4.5。
  • 确保您将UseTaskFriendlySynchronizationContext设置为true.

如果您需要在多个平台上的共享库中支持async,您可能会发现Microsoft.Bcl.Async NuGet库很有帮助。

票数 5
EN

Stack Overflow用户

发布于 2013-05-16 17:42:17

在ASP.NET中需要谨慎对待await,因为同步上下文希望序列化单个请求的工作。你发布的代码本身可能没问题-- await不会阻塞。但是,我预计在调用链中的某个位置,您将调用.Wait()或访问.Result,而不是await

这里有几个选项:

  • 根本不使用.Wait().Result (或类似的)-相反,只使用await并使其成为正确的异步操作
  • ,或者使用.ConfigureAwait(false)告诉它忽略同步上下文;不幸的是,这将需要添加到您await的所有位置,即

await ().ConfigureAwait(False);var db.ExecuteSomethingAsync(...).ConfigureAwait(false);

  • or,= await sql只使用同步代码-在大多数情况下,db.OpenAsync会运行得非常快-因此,将其推送到异步并不一定像您想象的那样有帮助;显然,这可能会因使用情况而异;但这里要记住的一个关键点是,ASP.NET本身就是线程化的-在

中,并不是整个服务器都会停止运行

票数 6
EN

Stack Overflow用户

发布于 2015-04-03 22:40:44

我注意到在用ASP.Net Web Forms代码分离编写异步/等待代码时需要牢记的另一个要点,那就是确保页面声明中的Async=“为真”。默认情况下,此属性为false。

如果您不这样做,那么您可能会看到您的页面处于永久加载状态。

代码语言:javascript
复制
<%@ Page Language="C#" Async="true" %>

此外,在.Net 4.5中,根据斯蒂芬的回答,我们需要在web配置应用程序设置部分将'UseTaskFriendlySynchronizationContext‘设置为true。另一个有用的应用程序设置是AllowAsyncDuringSyncStages,对于Webforms代码隐藏中的异步/等待代码,它需要为false。默认情况下,这两个设置都为false。

代码语言:javascript
复制
<add key="aspnet:AllowAsyncDuringSyncStages" value="false" />
<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true"/>

我在一个ASP.Net WebForm中使用了下面的async/await示例代码,它使用上面的设置并按照斯蒂芬的建议一直使用await,运行速度非常快。如果不遵循这些建议,那么您可能会看到see表单页面在浏览器中永远加载。

代码语言:javascript
复制
protected async void Page_Load(object sender, EventArgs e)
{
    if (!Page.IsPostBack)
    {
        string sql = @"DELETE FROM dbo.Table1
                       WHERE Processed = 1";
        SqlConnection conn = new SqlConnection(System.Configuration.ConfigurationManager.ConnectionStrings["MainDB"].ConnectionString);
        SqlCommand cmd = new SqlCommand(sql, conn);
        int numberOfRecordsUpdated = await UpdateDatabaseAsync(conn, cmd);
    }
}
public async Task<int> UpdateDatabaseAsync(SqlConnection conn, SqlCommand cmd)
{
    int i = 0;
    try
    {
        await conn.OpenAsync();
        i = await cmd.ExecuteNonQueryAsync();
    }
    catch (Exception ex)
    {
        //log the error
        Elmah.ErrorSignal.FromCurrentContext().Raise(ex);
    }

    finally
    {
        if (conn != null)
        {
            conn.Close();
            conn.Dispose();
        }
        if (cmd != null)
        {
            cmd.Dispose();
        }
    }
    return i;
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/16583792

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档