Nginx反向代理流式输出延迟?一招解决SSE/WebSocket缓冲问题SpringBoot+SSE流式输出卡住?Nginx这个配置必须关!

Nginx反向代理流式输出延迟?一招解决SSE/WebSocket缓冲问题

SpringBoot+SSE流式输出卡住?Nginx这个配置必须关!

Nginx代理后端流式响应要等好久才输出?完整解决方案来了

AI对话流式输出卡顿?Nginx proxy_buffering关闭指南

宝塔面板Nginx配置流式输出,90%的人都漏了这行配置

一、问题描述

最近在项目中使用 SpringBoot + SSE(Server-Sent Events) 实现流式输出功能(类似ChatGPT的打字机效果),发现前端接收数据时有明显延迟,需要等后端积累好多字才会输出一次,而不是实时逐字输出。

现象:

  • 后端已经返回数据,但前端迟迟收不到

  • 需要等待几秒甚至更久才一次性输出一大段

  • 流式效果完全失效,用户体验极差

环境:

  • Nginx 反向代理

  • 后端:SpringBoot

  • 协议:SSE / 流式响应

二、问题原因

Nginx 作为反向代理时,默认会开启响应缓冲(proxy_buffering),它会等后端响应达到一定大小后,才一次性发送给客户端。这对于普通HTTP请求没问题,但对于流式输出就是灾难。

核心原因:

Nginx 默认缓冲 → 数据积累到缓冲区阈值 → 才发送给客户端

三、解决方案

3.1 关键配置

在 Nginx 的 location 块中添加以下配置:

复制代码
location ^~ /jeecg-boot {
    proxy_pass              http://127.0.0.1:9191/jeecg-boot/;
    proxy_set_header        Host  $ Host;
    proxy_set_header        X-Real-IP  $ remote_addr;
    proxy_set_header        X-Forwarded-For  $ proxy_add_x_forwarded_for;
    proxy_set_header        Upgrade  $ http_upgrade;
    proxy_set_header        Connection "upgrade";
    
    # ⭐ 流式输出核心配置 ⭐
    proxy_buffering off;           # 关闭代理缓冲(最重要!)
    proxy_cache off;               # 关闭缓存
    proxy_request_buffering off;   # 关闭请求缓冲
    chunked_transfer_encoding on;  # 启用分块传输
    
    # 可选:设置较小的缓冲尺寸
    proxy_buffer_size 1k;
    proxy_buffers 4 1k;
    proxy_busy_buffers_size 2k;
    
    # 超时设置(防止长连接断开)
    proxy_connect_timeout 60s;
    proxy_send_timeout 300s;
    proxy_read_timeout 300s;
}

3.2 配置说明

配置项 作用 是否必须
proxy_buffering off 关闭响应缓冲,实时转发 ⭐ 必须
proxy_cache off 关闭缓存 推荐
proxy_request_buffering off 关闭请求缓冲 推荐
chunked_transfer_encoding on 启用分块传输编码 推荐
proxy_read_timeout 延长读取超时时间 长连接必须

四、后端配合配置

4.1 SpringBoot SSE 响应头

后端也需要设置正确的响应头,否则Nginx配置了也没用:

复制代码
@GetMapping(value = "/stream", produces = MediaType.TEXT_EVENT_STREAM_VALUE)
public Flux<ServerSentEvent<String>> stream() {
    return Flux.interval(Duration.ofMillis(100))
        .map(sequence -> ServerSentEvent.builder("数据:" + sequence)
            .build());
}

关键响应头:

复制代码
Content-Type: text/event-stream
Cache-Control: no-cache
Connection: keep-alive
X-Accel-Buffering: no

4.2 普通流式响应

复制代码
@GetMapping("/flow")
public void flow(HttpServletResponse response) throws IOException {
    response.setContentType("text/plain;charset=utf-8");
    response.setHeader("Cache-Control", "no-cache");
    response.setHeader("Connection", "keep-alive");
    response.setHeader("X-Accel-Buffering", "no");  // 关键!
    
    ServletOutputStream out = response.getOutputStream();
    for (int i = 0; i < 10; i++) {
        out.write(("数据" + i + "\n").getBytes(StandardCharsets.UTF_8));
        out.flush();  // 必须flush
        Thread.sleep(100);
    }
}

七、常见问题排查

7.1 配置后仍然有延迟?

  1. 检查是否有CDN:CDN也会缓冲,需要单独配置
  2. 检查Gzip:流式内容建议关闭gzip
  3. 检查后端是否flush :确保后端每次写入后都调用了flush()

7.2 连接频繁断开?

增加超时时间,并检查防火墙设置:

复制代码
proxy_send_timeout 600s;
proxy_read_timeout 600s;
keepalive_timeout 600s;

7.3 WebSocket也适用吗?

适用!WebSocket同样需要关闭缓冲,配置基本一致。

八、总结

表格

场景 关键配置
SSE流式输出 proxy_buffering off
WebSocket proxy_buffering off + Upgrade头
大文件下载 proxy_buffering off
AI对话流式 proxy_buffering off + 后端flush

核心就一行:proxy_buffering off;

但别忘了后端配合设置响应头和flush,否则还是不会实时输出!

九、参考资料


如果对你有帮助,欢迎点赞👍 收藏⭐ 关注💖

有问题欢迎在评论区留言讨论!

相关推荐
王琦031810 分钟前
第二次作业
linux·运维·服务器
Bert.Cai11 分钟前
Linux mkdir命令详解
linux·运维
chenglin01640 分钟前
AI服务的可观测性与运维
运维·人工智能
似水এ᭄往昔1 小时前
【Linxu】--进程优先级和进程切换
linux·运维·服务器
arvin_xiaoting2 小时前
OpenClaw学习总结_III_自动化系统_1:Hooks详解
运维·学习·自动化
海参崴-2 小时前
Linux进程管理完全指南
linux·运维·服务器
CQU_JIAKE2 小时前
4.4【A】
运维·服务器
kyle~2 小时前
Linux系统优化---PREEMPT_RT机器人开发方向
linux·运维·机器人
独隅2 小时前
在 Linux 上部署 TensorFlow 模型的全面指南
linux·运维·tensorflow
Strange_Head2 小时前
《Linux系统编程篇》Linux Socket 网络编程02 (Linux 进程间通信(IPC))——基础篇
linux·运维·网络