You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

通过jQuery Ajax调用异步方法出现阻塞无响应问题

异步API调用阻塞问题的解决方案

以下是前端发起异步请求的jQuery代码:

function retrieveSummary() {
    $.ajax({
        type: "POST",
        url: 'api/GetLeads',
        dataType: "json",
        async: true,
        error: function (xhr, textStatus, thrownError) {
        },
        success: function (data) {
        },
        failure: function (data) {
        }
    });
}

后端C#代码存在阻塞问题,注释已标注阻塞位置:

[HttpPost]
[ActionName("GetLeads")]
public List<Leads> GetSummary()
{
    List<Leads> list = new List<Leads>();
    
    var result = RunAsync(publicKey, secretKey).Result;
    var data = result.GetData();
    // 处理数据并返回,但在下方异步方法RunAsync的await行处阻塞
    .
    .
}

static async Task<Response> RunAsync(string publicKey, string secretKey)
{
    Client client = new Client(publicKey, secretKey);
    
    Request request = new Request()
    {
        Resource = Message.Resource
    };
    
    request.Filter(Message.Limit, limit)
        .Filter("FromTS", String.Format("{0:s}", fromDate))
        .Filter("ToTS", String.Format("{0:s}", toDate))
        .Filter("ShowContactAlt", "true")
        .Filter("ShowSubject", "true")
        .Filter("MessageStatus", 3)
        .Filter(Message.Offset, offSet);
    
    // Ajax请求在此处阻塞
    return await client.GetAsync(request);
}

问题根源

阻塞的核心原因是在同步方法中调用异步方法时使用了.Result。ASP.NET的请求上下文是单线程的,当你调用.Result时,当前线程会阻塞等待异步任务完成;而await client.GetAsync(request)执行完成后,需要回到原请求上下文继续处理,此时上下文已经被阻塞的线程占用,形成死锁。

修复方案

将控制器方法改为异步模式,全程使用await而非.Result:

[HttpPost]
[ActionName("GetLeads")]
// 改为异步方法,返回Task<List<Leads>>
public async Task<List<Leads>> GetSummary()
{
    List<Leads> list = new List<Leads>();
    
    // 用await替代.Result
    var result = await RunAsync(publicKey, secretKey);
    var data = result.GetData();
    // 处理数据并返回
    .
    .
}

// 保持RunAsync的异步逻辑不变
static async Task<Response> RunAsync(string publicKey, string secretKey)
{
    Client client = new Client(publicKey, secretKey);
    
    Request request = new Request()
    {
        Resource = Message.Resource
    };
    
    request.Filter(Message.Limit, limit)
        .Filter("FromTS", String.Format("{0:s}", fromDate))
        .Filter("ToTS", String.Format("{0:s}", toDate))
        .Filter("ShowContactAlt", "true")
        .Filter("ShowSubject", "true")
        .Filter("MessageStatus", 3)
        .Filter(Message.Offset, offSet);
    
    return await client.GetAsync(request);
}

关键说明

  • 异步方法需遵循异步全链路原则:从控制器入口到底层异步调用,全程使用async/await,避免同步阻塞异步任务
  • 不要在ASP.NET环境中使用.Result或.Wait()等待异步任务,这是死锁的常见诱因

内容的提问来源于stack exchange,提问作者Briskstar Technologies

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 08:05:26