在Heroku部署Django:Gunicorn与Nginx配置对比及最优方案
在Heroku部署Django时Gunicorn与Nginx的配置疑问
一、两种配置方式的核心区别
你找到的两套配置完全是不同层面的工具配置,作用天差地别:
1. systemd的Gunicorn配置(gunicorn.socket + gunicorn.service)
这是给传统Linux VPS/云服务器用的系统服务管理配置,核心是管Gunicorn进程的生命周期:
gunicorn.socket:创建一个Unix套接字,当有请求接入时自动触发Gunicorn启动,避免进程闲置占用资源gunicorn.service:定义Gunicorn的运行规则——指定运行用户、工作目录、启动参数(绑定套接字、设置worker数量等)
简单说,这套配置是让Gunicorn能像系统自带服务一样,开机自启、崩溃自动重启,不用你手动去后台维护进程。
2. Nginx官方的反向代理配置
这是Nginx的核心请求路由配置,管的是外部请求的分发与HTTP协议处理:
- 监听80端口接收用户的HTTP请求
- 优先处理静态文件请求(比如CSS、JS、图片),直接返回资源;非静态请求则转发给Gunicorn处理
- 同时负责处理请求头、超时控制、错误页面等HTTP层面的细节
这套配置是整个服务的入口,把外部请求合理分发给Gunicorn,同时承担静态资源的高效服务。
两者的本质差异:
- systemd配置是进程管理工具,解决Gunicorn怎么稳定持续运行的问题
- Nginx配置是反向代理规则,解决外部请求怎么到达Gunicorn的问题
二、Heroku上的最优配置方案
Heroku是PaaS平台,和传统VPS的运行逻辑完全不同——它自带反向代理层,也不需要你手动配置systemd管理进程,直接套用VPS的配置行不通,得按Heroku的规则来:
1. Gunicorn基础配置(必做)
在项目根目录创建Procfile,这是Heroku识别启动命令的核心文件,内容如下:
web: gunicorn myproject.wsgi:application --workers=3 --bind=0.0.0.0:$PORT
web:告诉Heroku这是处理HTTP请求的进程--workers=3:按Gunicorn推荐的公式,worker数量设为2*CPU核心数+1,Heroku基础dyno是1核,所以3个刚好--bind=0.0.0.0:$PORT:必须绑定到Heroku动态分配的$PORT环境变量,不能用Unix套接字(Heroku容器环境不推荐这么用)
如果需要更精细的Gunicorn配置,可以在根目录创建gunicorn.conf.py:
workers = 3 bind = "0.0.0.0:$PORT" accesslog = "-" # 日志输出到stdout,方便Heroku收集查看 errorlog = "-" timeout = 120 # 避免长请求超时被中断
2. Nginx配置(可选但推荐)
Heroku自带反向代理,但如果需要更高效的静态资源缓存、请求过滤,你可以用Heroku的nginx-buildpack添加Nginx层:
- 添加buildpack:
用命令行或Heroku控制台设置:heroku buildpacks:add https://github.com/heroku/heroku-buildpack-nginx - 创建
nginx.conf.erb配置文件(erb格式是为了读取Heroku环境变量):
worker_processes <%= ENV['NGINX_WORKER_PROCESSES'] || 1 %>; daemon off; pid /tmp/nginx.pid; error_log <%= ENV['NGINX_ERROR_LOG_PATH'] || 'stderr' %> warn; events { worker_connections <%= ENV['NGINX_WORKER_CONNECTIONS'] || 1024 %>; } http { include mime.types; default_type application/octet-stream; sendfile on; tcp_nopush on; keepalive_timeout 65; upstream app_server { server unix:/tmp/nginx.socket fail_timeout=0; } server { listen <%= ENV['PORT'] %>; client_max_body_size 4G; # 静态资源处理,添加缓存策略 location /static/ { alias <%= ENV['STATIC_ROOT'] %>/; expires 30d; add_header Cache-Control "public, immutable"; } # 媒体文件处理 location /media/ { alias <%= ENV['MEDIA_ROOT'] %>/; } # 动态请求转发给Gunicorn location / { proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; proxy_set_header Host $http_host; proxy_redirect off; proxy_pass http://app_server; } } }
- 修改
Procfile,让Nginx先启动,再转发请求给Gunicorn:
web: bin/start-nginx gunicorn myproject.wsgi:application --workers=3 --bind=unix:/tmp/nginx.socket
3. 必备额外配置
- 静态资源:在
settings.py里设置STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles'),部署时Heroku会自动执行python manage.py collectstatic(需确保DEBUG=False) - 环境变量:在Heroku控制台设置
DEBUG=False、数据库URL、SECRET_KEY等关键参数,绝对不要硬编码在代码里
内容的提问来源于stack exchange,提问作者Tùng Nguyễn
相关产品推荐
相关产品推荐

