如何部署同时集成WSGI与ASGI应用的Django项目
Django同时部署WSGI与ASGI应用的可行方案
两类接口规范无法通过单一声明直接同时挂载,通用实现思路是做请求分流,将不同类型的请求转发到对应的处理服务即可,以下是两种生产环境可用的实现方案:
方案1:Nginx反向代理分流(推荐,适合生产环境)
- 首先基于同一份项目代码启动两个独立的后端服务实例:
- WSGI服务用
gunicorn或uWSGI启动,入口指向项目自动生成的wsgi.py,监听本地端口比如127.0.0.1:8000,用于处理常规HTTP请求 - ASGI服务用
uvicorn或daphne启动,入口指向项目自动生成的asgi.py,监听本地端口比如127.0.0.1:8001,用于处理Websocket、异步视图等需要异步能力的请求
- WSGI服务用
- 配置Nginx反向代理规则,根据路径/协议匹配转发到对应后端,示例配置片段如下:
# 常规HTTP请求转发到WSGI服务 location / { proxy_pass http://127.0.0.1:8000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } # 异步/Websocket请求转发到ASGI服务 location /ws/ { proxy_pass http://127.0.0.1:8001; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; proxy_set_header Host $host; }
- 该方案两个服务独立运行,可分别扩缩容,故障不会互相影响,稳定性最高。
方案2:ASGI服务兼容挂载WSGI应用(适合中小流量场景)
如果不想维护两个服务进程,可以用a2wsgi工具在ASGI服务内兼容WSGI应用,实现单进程分流:
- 首先安装依赖:
pip install a2wsgi - 修改项目的
asgi.py文件,将WSGI应用挂载到指定路由:
import os from django.core.asgi import get_asgi_application from django.core.wsgi import get_wsgi_application from a2wsgi import WSGIMiddleware os.environ.setdefault("DJANGO_SETTINGS_MODULE", "你的项目名.settings") django_asgi_app = get_asgi_application() # 把WSGI应用封装为ASGI兼容的中间件 django_wsgi_app = WSGIMiddleware(get_wsgi_application()) async def application(scope, receive, send): # 自定义分流规则,非websocket的常规请求走WSGI应用 if scope["type"] == "http" and not scope["path"].startswith("/ws/"): await django_wsgi_app(scope, receive, send) else: await django_asgi_app(scope, receive, send)
- 之后仅需启动一个Uvicorn服务监听对外端口即可,无需额外配置反向代理规则。
通用注意事项
- 无论用哪种方案,都建议将Django的会话、缓存配置为Redis等共享存储,不要使用默认的本地内存存储,避免不同进程间数据不一致。
内容的提问来源于stack exchange,提问作者İsmail DERVİŞOĞLU
相关产品推荐
相关产品推荐

