聊天页每隔 60 秒断一次,前端 onclose 收到 code 1006,重连后历史消息重复拉取。乍看像缓存或者权限的锅,追下去往往不是。
location /ws/ {
proxy_pass http://ws_backend;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_read_timeout 3600s;
}
追下去是这么回事:Nginx 默认 60 秒没有读到上游数据就关连接,WebSocket 空闲时正好没有帧。Upgrade 和 Connection 头没转发时,握手也降级成普通 HTTP。
「反代 WebSocket 断开」相关的验证我通常做两遍,改完一次、隔天再看一次,确认不是临时生效。验证用真实数据走一遍,测试数据太干净,边界情况根本碰不到。
能分两步做的操作就别合成一步,中间看一眼返回值,出问题好判断。报错里带路径的,先去看那个路径在不在、权限对不对。
同一份配置存在多处的,先确认改的是被加载的那一份。新版本先放一台机器上跑一天再全量,问题一般在这段时间暴露。
备份不是备了就行,恢复一次才算数,很多备份文件打开才发现是空的。
具体做法是,location 里设 proxy_http_version 1.1;转发 Upgrade 和 Connection 头 值用 upgrade;proxy_read_timeout 提到 3600s 或按心跳周期设;应用层加 ping 帧 保持连接有数据。
验收就看一点,连接保持 10 分钟不断 onclose 不再出现 1006。
