首页 > 解决方案 > 如何在 MVC 中执行 await 方法

问题描述

我们正在使用 Microsoft Graph SDK。在控制台应用程序中实现了一个 POC,其中代码工作正常,但在 MVC 中添加此代码时它不起作用。代码卡在等待调用

从控制器调用

 [HttpPost]
    public ActionResult InviteUser([Bind(Include = "EmailId")] UserLogin userLogin)
    {
        if (ModelState.IsValid)
        {
            string result = AzureADUtil.InviteUser(userLogin.EmailId);
        }
        return View();
    }

方法实现如下

  public static string InviteUser(string emailAddress)
    {
        string result = string.Empty;

        result = InviteNewUser(emailAddress).Result;

        return result;

    }

    private static async Task<string> InviteNewUser(string emailAddress)
    {
        string result = string.Empty;
        try
        {
            IConfidentialClientApplication confidentialClientApplication = ConfidentialClientApplicationBuilder
            .Create(clientId)
            .WithTenantId(tenantID)
            .WithClientSecret(clientSecret)
            .Build();

            ClientCredentialProvider authProvider = new ClientCredentialProvider(confidentialClientApplication);

            GraphServiceClient graphClient = new GraphServiceClient(authProvider);

            // Send Invitation to new user
            var invitation = new Invitation
            {
                InvitedUserEmailAddress = emailAddress,
                InviteRedirectUrl = "https://myapp.com",
                SendInvitationMessage = true,
                InvitedUserType = "Member" 

            };

            // It stucks at this line
            await graphClient.Invitations
            .Request()
            .AddAsync(invitation);

        }
        catch (Exception ex)
        {
            result = ex.Message;
        }
        return result;

    }

标签: c#asp.net-mvcasync-await

解决方案


混合 async-await 和阻塞代码,例如.Result.Wait()倾向于导致死锁,尤其是在 asp.net-mvc 上。

如果要异步,那么就一直走。

[HttpPost]
public async Task<ActionResult> InviteUser([Bind(Include = "EmailId")] UserLogin userLogin) {
    if (ModelState.IsValid) {
        string result = await AzureADUtil.InviteUser(userLogin.EmailId);
    }
    return View();
}

随着实现也被重构为异步

public static async Task<string> InviteUser(string emailAddress)
{
    string result = string.Empty;

    result = await InviteNewUser(emailAddress);

    return result;
}

InviteUser现在是多余的,因为它基本上包装了私人InviteNewUser电话。

参考Async/Await - 异步编程的最佳实践


推荐阅读