feat(stage): nginx 加 /ws/ location(推論 inference WS + 其餘 /ws/* stub)

兩個 server block(公網 stage-9527 + 內網 IP 直連 192.168.0.130)各加
一條 location /ws/ → proxy_pass api-server(:3721)。缺這條時 /ws/* 會落到
catch-all → Next.js → 404,擋住前端推論頁 WS 握手。

- WS upgrade 三要素(http/1.1 + Upgrade + Connection $connection_upgrade)
- 長 timeout 86400s + proxy_buffering off(比照 /tunnel/connect)
- 不影響既有 /tunnel/connect(不同 path 前綴、互不 shadow)
- 兩 block header 對齊(含 X-Forwarded-Host)

驗證:/ws/devices/test-id/inference 不帶 cookie → 401(過 backend auth)
不再 404;/tunnel/connect 回歸 401;preset 下載 200/206;demo 設定保留。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
jim800121chen 2026-07-09 06:00:59 +08:00
parent 0010cc35c3
commit 81a32a5bf8

View File

@ -292,6 +292,45 @@ server {
proxy_set_header X-Forwarded-Proto https;
}
# ============================================================
# /ws/* → api-server :3721 (推論 inference WS + 既有 pairing/events/system WS)
#
# ⚠️ 為什麼必須有這條 location
# 下方 catch-all `location /` 反代到 Next.js frontend (:3000)。若沒有這條,
# /ws/devices/:id/inference 等所有 /ws/* 會落到 frontend → Next 沒有此 route
# → 404前端推論頁的 WS 握手斷掉。必須在 catch-all 之前用前綴 location 攔下,
# 導到 api-server (:3721),該處掛 wsAuthGroup/ws/devices/:id/inference 需 auth
# 與 registerWebSocketStubs其餘 /ws/* 目前 501 stub
#
# 與 /tunnel/connect 的關係:兩者是不同 path 前綴(/ws/ vs /tunnel/connect
# nginx 前綴 location 各自最長匹配、互不 shadow。/ws/ 不會吃到 /tunnel/connect。
#
# WS upgrade 三要素 + 長 timeout + buffering off比照 /tunnel/connect。
# $connection_upgrade 繼承自 http-context map檔頭 38-41 行)。
# cookie 由 proxy_pass 預設透傳inference WS 走 cookie/session auth
# ============================================================
location /ws/ {
proxy_pass http://visiona_api;
proxy_http_version 1.1;
# WebSocket upgrade headers
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
# 推論 WS 為 long-lived 串流;拉長 timeout比照 /tunnel/connect
proxy_read_timeout 86400s;
proxy_send_timeout 86400s;
# 不 buffer避免延遲 WS 訊框
proxy_buffering off;
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 X-Forwarded-Proto https;
proxy_set_header X-Forwarded-Host $host;
}
# ============================================================
# Next.js hashed static assets — 永久 cache
# /_next/static/{hash}.js 等
@ -480,6 +519,29 @@ server {
proxy_set_header X-Forwarded-Proto http;
}
# ── /ws/* → api-server :3721推論 inference WS + 其餘 /ws/* stub──
# 完整比照 stage-9527 block 的 /ws/ 設定http/1.1 + Upgrade + Connection
# + 86400s timeout + buffering off。$connection_upgrade 繼承自 http-context map。
# 不會 shadow 上面的 /tunnel/connect不同 path 前綴)。
location /ws/ {
proxy_pass http://visiona_api;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_read_timeout 86400s;
proxy_send_timeout 86400s;
proxy_buffering off;
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 X-Forwarded-Proto http;
proxy_set_header X-Forwarded-Host $host;
}
# ── Next.js hashed static內網瀏覽器用──
location /_next/static/ {
proxy_pass http://visiona_frontend;