nginx日志磁盘写满会导致服务假死、502/504错误及上传失败。需用df -h和lsof +l1快速定位,清空日志文件而非删除,并通过logrotate实现自动轮转压缩防复发。

日志磁盘写满是 Nginx 在生产环境中最常见、也最容易被低估的故障诱因。它不会立刻报错,但会悄悄让服务变慢、响应异常,甚至导致进程“假死”——看似在运行,实则无法处理新请求。关键在于:磁盘满后,Nginx 仍可能保持 master 进程存活,而 worker 进程因无法写入 error.log 或创建临时文件而卡住或退出,最终表现为 502/504、上传失败、缓存失效等现象。
一、快速确认是否为磁盘满引发的挂起
别急着重启,先验证根源:
- 执行 df -h,重点看
/var/log、/var/lib/nginx、/tmp所在分区是否达到 95%+; - 用 ls -lSh /var/log/nginx/ 查看 access.log 和 error.log 是否异常巨大(比如单个超 1GB);
- 运行 lsof +L1 | grep deleted,若输出包含 nginx 相关日志文件,说明你已删过日志但进程仍在持有句柄——这是典型“删了没释放”的挂起信号;
- 检查 ps aux | grep nginx:如果只有 master 进程,没有 worker 进程,或 worker 进程状态为
Z(僵尸)或 CPU 占用长期为 0,基本可锁定。
二、应急恢复:清空间 + 释放句柄
目标是让 Nginx 立刻恢复服务能力,不中断主进程:
- 清空日志内容而非删除文件:echo "" > /var/log/nginx/access.log 和 echo "" > /var/log/nginx/error.log(避免丢失句柄);
- 若已误删且
lsof +L1显示被占用,需强制释放:先 kill -USR1 $(cat /var/run/nginx.pid)(触发日志 reopen),再对残留的 deleted 文件执行 kill -HUP 对应 worker 进程 PID; - 更稳妥做法是 reload:nginx -s reload,但前提是配置无误;若 reload 失败或 worker 无响应,直接 kill -9 所有 nginx worker 进程(保留 master),系统会自动拉起新 worker;
- 最后再次 df -h 确认磁盘释放成功,并观察 tail -f /var/log/nginx/error.log 是否开始正常写入。
三、防复发:从机制上堵住日志膨胀漏洞
靠人工清理永远滞后,必须落地自动化策略:
- 启用 logrotate 并配全参数:每日轮转、保留 7 天、自动压缩、空文件跳过(
daily rotate 7 compress missingok notifempty); - 在 nginx 配置中限制日志粒度:关闭调试级日志(
error_log /var/log/nginx/error.log warn;),对非核心 location 关闭 access_log(access_log off;); - 设置磁盘水位告警:用 df -h | awk '$5+0 > 85 {print $0}' 定时巡检,配合邮件或钉钉通知;
- 给 nginx 临时目录(如
client_body_temp_path)单独挂载小容量磁盘,避免日志挤占核心服务空间。
四、延伸排查:磁盘满只是表象,背后常藏配置缺陷
频繁磁盘告警往往暴露更深层问题:
- 检查是否启用了未压缩的 JSON 日志格式,或记录了敏感字段(如完整 request body),导致日志体积暴增;
- 确认是否有错误配置导致循环重定向、无限重试,从而产生海量 302/502 日志;
- 查看
error.log中是否高频出现no live upstreams、connect() failed等错误——这说明后端失联,Nginx 正在疯狂记错,需同步修复依赖服务; - 若使用容器部署,注意宿主机日志驱动配置(如 json-file 的 max-size/max-file),避免容器层日志失控。











