正确代理 WebSocket 需在 location 块中配置 proxy_set_header Upgrade $http_upgrade; 和 proxy_set_header Connection $connection_upgrade;,并启用 proxy_http_version 1.1; 及 http 级 map 块定义 $connection_upgrade。

要在 Nginx 中正确代理 WebSocket,关键不是加一堆可选参数,而是确保 Upgrade 和 Connection 这两个逐跳头被准确透传——它们是 WebSocket 握手成功的必要条件。Nginx 默认会丢弃这两个头,必须显式配置,且必须放在具体匹配路径的 location 块内。
必须写对的两行 header 配置
这两行必须同时存在、位置正确、写法规范:
-
proxy_set_header Upgrade $http_upgrade;:把客户端原始的Upgrade: websocket头原样传给后端。变量$http_upgrade是 Nginx 内置的,自动提取请求中的 Upgrade 值(如websocket) -
proxy_set_header Connection $connection_upgrade;:用动态变量$connection_upgrade,而非固定字符串。它会根据$http_upgrade是否存在自动设为upgrade或close,更安全可靠
前提条件:HTTP/1.1 协议强制启用
Upgrade 机制只在 HTTP/1.1 中定义,所以必须加这一行:
-
proxy_http_version 1.1;:不能省略,也不能写成1.0或留空。这是协议升级的基础支撑
配套 map 块(推荐放在 http 级别)
要让 $connection_upgrade 变量生效,需提前在 http{} 块中定义映射规则:
map $http_upgrade $connection_upgrade { default upgrade; '' close; }- 这行不是可选优化,而是启用
$connection_upgrade的必要前提;如果直接写"upgrade"字符串虽能工作,但会丢失对非 Upgrade 请求的兼容性
常见错误写法(务必避开)
- 写成
proxy_set_header Connection "upgrade"(硬编码字符串):看似简单,但无法适配非 WebSocket 请求,可能干扰普通 HTTP 流量 - 漏掉
map块却用了$connection_upgrade:Nginx 启动会报错或变量为空,导致 Connection 头缺失 - 把这两行写在根 location(如
location / { })里:容易误伤其他接口,且路径匹配不精准,WebSocket 子路径(如/ws/v2/chat)可能无法正确路由


















