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

Django ASGI+Uvicorn多线程异常:同步/异步视图线程疑问

ASGI服务器在同步/异步视图下的线程行为分析

测试场景与观测现象

  • 搭建测试项目包含两个核心视图:
    • 同步视图:基于time.sleep实现阻塞逻辑
    • 异步视图:基于asyncio.sleep实现非阻塞异步逻辑
  • 并发请求测试结果:
    • 同步视图:500个并发请求触发服务器创建500个线程,与单线程串行处理的预期不符
    • 异步视图:500个并发请求同样触发服务器创建500个线程,但日志显示所有请求实际由单个线程完成处理
  • 对比测试:Uvicorn搭配FastAPI的组合中,异步代码处理符合预期,全程仅使用单个线程
  • 变量排除:测试过程未引入任何含同步代码的中间件或额外应用

核心原因拆解

  1. 同步视图的线程池调度逻辑
    ASGI服务器(如默认配置的Django ASGI)为了防止同步阻塞代码卡死整个事件循环,会自动将同步视图的执行任务调度到线程池中。当并发请求数超过线程池默认上限时,服务器会动态扩容线程池,这就导致了500个请求对应500个线程的情况——本质是用线程池隔离同步阻塞操作,保障主事件循环的可用性。

  2. 异步视图的线程"假象"
    观测到的500个线程是ASGI服务器(如Uvicorn)的线程池预留/初始化机制,并非实际用于处理异步请求。异步视图的代码会直接在主事件循环中执行,asyncio.sleep这类非阻塞操作会让事件循环在等待期间切换处理其他请求,因此日志显示的单线程处理是真实状态,额外线程是服务器为潜在同步任务预留的冗余资源,并未参与异步请求的实际处理。

  3. Uvicorn+FastAPI的行为差异
    FastAPI是纯异步优先框架,且Uvicorn搭配FastAPI时,默认线程池配置更保守,同时FastAPI的路由机制会严格将异步请求绑定到主事件循环,避免了线程池的不必要初始化,因此表现为单线程处理异步请求。

异步视图示例代码

async def view(_):
    await asyncio.sleep(5)
    return HttpResponse("hello world")

内容的提问来源于stack exchange,提问作者usama bin khalid

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.18 00:22:22