直接调优 dirty_ratio 不能提升 Nginx 大文件上传写入性能,反而易引发系统风险;应协同调整 background_ratio、expire_centisecs 和 writeback_centisecs,并优先采用关闭 proxy_request_buffering、增大 buffer、启用 sendfile 等更安全有效的方法。

直接调优 dirty_ratio 不能提升 Nginx 代理大文件上传的写入性能,反而容易引发系统级风险。它不是为 Nginx 日志或上传场景设计的“性能开关”,而是 Linux 内核对全部脏页(所有进程修改但未落盘的内存页) 的全局强制同步阈值。
当大文件上传持续进行时,Nginx(尤其是开启 client_body_buffer_size 后)和后端服务都会向页缓存写入大量数据。若 dirty_ratio 设置过高(如 40 或 60),系统会允许脏页堆积到接近内存上限才触发刷盘;一旦触发,内核必须同步阻塞所有写进程(包括 Nginx worker)来紧急回写——这会导致上传卡顿、超时、连接重置,甚至拖垮整个服务器响应。
真正影响大文件上传写入流畅性的,是脏页能否被及时、平滑地异步刷出,而不是“堆得更多再猛冲一次”。
关键协同参数需一起调整
-
vm.dirty_background_ratio:设为 5–10(默认常为 20)。这是后台刷盘线程(writeback)启动的软门槛。值越低,刷盘越早开始,避免脏页逼近dirty_ratio边缘。 -
vm.dirty_expire_centisecs:建议设为 30000(5 分钟) 或更高。延长脏页在内存中可停留的最大时间,缓解突发上传造成的瞬时压力,让刷盘节奏更可控。 -
vm.dirty_writeback_centisecs:可设为 500(5 秒),让内核更频繁唤醒刷盘线程检查是否需要工作,避免长时间空闲后集中爆发。
✅ 示例:
echo 'vm.dirty_background_ratio = 8' >> /etc/sysctl.conf echo 'vm.dirty_ratio = 25' >> /etc/sysctl.conf echo 'vm.dirty_expire_centisecs = 30000' >> /etc/sysctl.conf echo 'vm.dirty_writeback_centisecs = 500' >> /etc/sysctl.conf sysctl -p
比调内核参数更有效、更安全的做法
-
关闭
proxy_request_buffering:让 Nginx 边收边转上传体,彻底绕过整体会话体缓存,内存占用恒定,不生成大量脏页。 -
增大
client_body_buffer_size到 128k~512k:减少小块临时文件写入频次;配合client_body_temp_path指向 SSD 目录,降低磁盘 I/O 延迟。 -
启用
sendfile on+tcp_nopush on:对静态大文件响应路径(如下载回源)显著减少拷贝与系统调用。 - 用 syslog 转发替代本地日志写入:将 access_log 输出到 rsyslog(disk-assisted 模式),完全解耦 Nginx 主流程与磁盘写入压力。
务必监控,而非盲调
调参前先确认是否真是脏页瓶颈:
# 实时查看脏页占比
grep -i dirty /proc/meminfo
# 观察每秒刷盘量(单位:kB)
awk '/pgpgout/ {print $2*4}' /proc/vmstat
# 查看脏页积压趋势(持续高于 70% dirty_ratio 就危险)
watch -n 1 'grep -i "dirty.*ratio\|Dirty:" /proc/meminfo'
不复杂但容易忽略:内核脏页参数优化,本质是“削峰填谷”,不是“加宽水坝”。重点在让写入压力分散、可预期,而不是堆到临界点再硬扛。











