核心是禁用nginx默认缓冲实现流式透传:上传需关proxy_request_buffering和proxy_buffering、透传关键头、调大client_max_body_size;下载需关proxy_buffering并确保后端流式响应;同步延长超时、启用http/1.1长连接、提升系统文件句柄限制。

核心是让 Nginx 不缓存整个请求或响应体,改为边收边发的流式透传。默认缓冲机制在处理大文件上传或下载时极易耗尽内存或填满临时磁盘,导致 worker 崩溃、502/504 错误或 OOM killer 杀进程。
上传场景:禁用 request body 预读与代理缓冲
大文件上传(如 2GB 视频、分片上传)最常因 proxy_request_buffering 开启而失败——Nginx 会等完整文件收完才转发,造成内存暴涨、超时卡在 99%。
- 必须在对应
location块中关闭:proxy_request_buffering off;(Nginx 1.7.11+,仅 location 级生效) - 同步关闭代理响应缓冲:
proxy_buffering off;,避免上传回调或进度响应也被缓存阻塞 - 确保透传关键上传头:
proxy_pass_request_headers on;,并显式保留Range、If-Range、Content-Range等断点续传所需字段 - 不要遗漏基础限制:
client_max_body_size 20G;(需放在server或http块,否则 413 直接拦截)
下载场景:关闭缓冲 + 确保后端流式响应
反向代理下载超大视频或导出文件时,内存溢出主因是 proxy_buffering on 强制缓存整段响应再下发,导致内存和临时磁盘双压。
FastAPI + Flask 混合部署最佳实践,解决路由定义、API 代理等常见问题,适用于同时运行 FastAPI API 与 Flask 前端的场景。
- 直接关闭缓冲:
proxy_buffering off;—— 此时 Nginx 只做字节流透传,内存恒定在 KB 级 - 必须确认后端返回合法流式响应:含
Content-Length或使用Transfer-Encoding: chunked,否则连接可能挂起 - 若需保留缓冲(如需头改写、重试),则严格控盘:
proxy_temp_path /data/nginx/proxy_temp 1 2;(指向空间充足、非 tmpfs 的分区),并设proxy_max_temp_file_size 4096m; - 禁用默认
/tmp作临时路径,它常为内存盘,写大文件等于直接耗尽 RAM
配套必须调优的超时与系统限制
关闭缓冲后,传输周期变长,原有 60 秒超时会频繁中断;同时高并发下系统资源不足也会触发崩溃。
- 延长关键超时:
client_body_timeout 3600;、proxy_read_timeout 3600;、proxy_send_timeout 3600; - 启用 HTTP/1.1 长连接:
proxy_http_version 1.1;+proxy_set_header Connection '';,防中间设备断连 - 提升系统级文件句柄限制:在
/etc/systemd/system/nginx.service.d/override.conf中加LimitNOFILE=1048576,再重载服务 - 检查后端是否同步放宽限制(如 Spring Boot 的
spring.servlet.multipart.max-file-size)
不推荐但需知的“缓冲调大”误区
有人试图通过增大 proxy_buffers 或 proxy_buffer_size 解决问题,这在大文件场景适得其反:
-
proxy_buffer_size只用于响应头,设过大(如 128k)会让每个连接多占内存,无实际收益 -
proxy_buffers 32 64k意味着单连接预占 2MB 内存,万级并发即消耗 20GB+,极易触发 OOM - 真正要调的是
proxy_max_temp_file_size和磁盘路径,而非盲目堆内存缓冲 - header 处理异常(如
upstream sent too big header)应优先精简后端响应头,而非调大proxy_headers_hash_bucket_size










