fix: gunicorn.conf.py 从 sync 改为 gthread,修复全站卡死根因
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
37
deploy/audit-system.sh
Normal file
37
deploy/audit-system.sh
Normal file
@@ -0,0 +1,37 @@
|
||||
#!/bin/bash
|
||||
# 系统级排查:Gunicorn 是否双开、是否用了错误的 sync 配置
|
||||
set -e
|
||||
echo "========== Gunicorn 进程(看 worker_class / 是否双开)=========="
|
||||
pgrep -af gunicorn || echo "无 gunicorn"
|
||||
|
||||
echo ""
|
||||
echo "========== 8001 端口占用 =========="
|
||||
ss -ltnp 2>/dev/null | grep 8001 || netstat -ltnp 2>/dev/null | grep 8001 || echo "8001 未监听"
|
||||
|
||||
echo ""
|
||||
echo "========== systemd 实际启动命令 =========="
|
||||
systemctl cat gunicorn-dianjing.service 2>/dev/null | grep -E '^ExecStart|^Environment' || echo "无 systemd service"
|
||||
|
||||
echo ""
|
||||
echo "========== gunicorn.conf.py 关键项 =========="
|
||||
CONF="/opt/1panel/apps/openresty/nginx/www/sites/43.142.166.152.443/django/gunicorn.conf.py"
|
||||
if [ -f "$CONF" ]; then
|
||||
grep -E 'worker_class|workers|threads|accesslog|errorlog|preload' "$CONF" | grep -v '^#'
|
||||
else
|
||||
echo "找不到 $CONF"
|
||||
fi
|
||||
|
||||
echo ""
|
||||
echo "========== 判定 =========="
|
||||
NG=$(pgrep -cf 'gunicorn.*a_long_dianjing' 2>/dev/null || echo 0)
|
||||
if [ "$NG" -gt 8 ]; then
|
||||
echo ">>> 警告: gunicorn 进程过多($NG),可能 systemd + 1Panel 双开,必须只留 systemd"
|
||||
fi
|
||||
if grep -q 'worker_class.*sync' "$CONF" 2>/dev/null; then
|
||||
echo ">>> 致命: gunicorn.conf.py 仍是 sync,全站会卡死,必须改为 gthread 并 restart"
|
||||
fi
|
||||
if grep -q 'accesslog.*"-' "$CONF" 2>/dev/null || grep -q "accesslog = '-'" "$CONF" 2>/dev/null; then
|
||||
echo ">>> 致命: accesslog 输出到 stdout,会灌 journal 卡整机"
|
||||
fi
|
||||
echo ""
|
||||
echo "正确做法: 1Panel 关闭 Python 自动管理 → git pull → bash deploy/safe-deploy.sh"
|
||||
@@ -7,7 +7,7 @@ Type=simple
|
||||
User=root
|
||||
Group=root
|
||||
WorkingDirectory=/opt/1panel/apps/openresty/nginx/www/sites/43.142.166.152.443/django
|
||||
ExecStart=/usr/local/bin/gunicorn --bind 127.0.0.1:8001 --workers 6 --threads 4 --worker-class gthread --timeout 120 --log-level warning --access-logfile /dev/null --error-logfile /tmp/gunicorn-error.log a_long_dianjing.wsgi:application
|
||||
ExecStart=/usr/local/bin/gunicorn -c gunicorn.conf.py a_long_dianjing.wsgi:application
|
||||
Restart=always
|
||||
RestartSec=3
|
||||
StandardOutput=null
|
||||
|
||||
@@ -1,52 +1,32 @@
|
||||
# /opt/1panel/apps/openresty/nginx/www/sites/43.142.166.152.443/django/gunicorn.conf.py
|
||||
# Gunicorn 生产配置(systemd 与 1Panel 共用此文件,勿再手写冲突参数)
|
||||
# 安装后: systemctl restart gunicorn-dianjing.service
|
||||
|
||||
# 绑定的IP和端口(根据你的Nginx配置,后端在8001端口)
|
||||
bind = "127.0.0.1:8001"
|
||||
|
||||
# 工作进程数(根据CPU核心数调整,建议:CPU核心数*2+1)
|
||||
# 查看CPU核心数:cat /proc/cpuinfo | grep "processor" | wc -l
|
||||
workers = 4
|
||||
# 必须用 gthread:sync 模式下 4 worker 同时只能处理 4 个请求,远程 MySQL 一慢就全站卡死
|
||||
workers = 6
|
||||
threads = 4
|
||||
worker_class = "gthread"
|
||||
|
||||
# 工作模式(使用gevent支持异步,更高效)
|
||||
#worker_class = "gevent"
|
||||
worker_class = "sync" # 改成这个
|
||||
|
||||
# 每个worker的最大请求数(防止内存泄漏)
|
||||
max_requests = 1000
|
||||
max_requests_jitter = 50 # 随机抖动,避免所有worker同时重启
|
||||
|
||||
# 超时时间(秒)
|
||||
timeout = 30
|
||||
timeout = 120
|
||||
graceful_timeout = 30
|
||||
keepalive = 2
|
||||
|
||||
# 预加载应用(减少内存占用,加快请求处理)
|
||||
preload_app = True
|
||||
max_requests = 2000
|
||||
max_requests_jitter = 100
|
||||
|
||||
# 日志配置
|
||||
# 访问日志:输出到标准输出,便于OnePanel查看
|
||||
accesslog = "-"
|
||||
# 错误日志:输出到标准错误
|
||||
errorlog = "-"
|
||||
# 日志级别
|
||||
loglevel = "info"
|
||||
# 禁止输出到 stdout/stderr(曾灌满 journal 导致整机卡)
|
||||
accesslog = None
|
||||
errorlog = "/tmp/gunicorn-error.log"
|
||||
loglevel = "warning"
|
||||
|
||||
# gthread + MySQL 连接池:preload 易在 fork 后出连接问题
|
||||
preload_app = False
|
||||
|
||||
# 进程名称(便于识别)
|
||||
proc_name = "a_long_dianjing_gunicorn"
|
||||
|
||||
# 工作进程的用户/组(安全考虑,用非root用户运行)
|
||||
# user = "www-data"
|
||||
# group = "www-data"
|
||||
|
||||
# 工作进程临时目录(避免权限问题)
|
||||
worker_tmp_dir = "/dev/shm"
|
||||
daemon = False
|
||||
|
||||
# 限制请求数据大小(防止大文件攻击)
|
||||
limit_request_line = 4094
|
||||
limit_request_fields = 100
|
||||
limit_request_field_size = 8190
|
||||
|
||||
# 优雅退出时间
|
||||
graceful_timeout = 30
|
||||
|
||||
# 进程守护(如果用systemd管理,这里设为False)
|
||||
daemon = False
|
||||
Reference in New Issue
Block a user