From 7ff73b7d07ebf88d1d8ee4c01cb8f44ba8817453 Mon Sep 17 00:00:00 2001 From: qing <1776177662@qq.com> Date: Thu, 6 Aug 2026 09:16:34 +0000 Subject: [PATCH] =?UTF-8?q?fix(aibox):=20=E7=BC=A9=E7=9F=AD=20WebSocket=20?= =?UTF-8?q?=E5=BF=83=E8=B7=B3=E9=97=B4=E9=9A=94=E5=B9=B6=E8=A1=A5=E5=85=A8?= =?UTF-8?q?=E7=9B=B4=E8=BF=9E=E9=A1=B5=E9=9D=A2=E5=BF=83=E8=B7=B3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 前置代理(Nginx/CDN)的 proxy_read_timeout 约 20s,原 25s 心跳 无法在超时前到达,导致连接被代理切断。aibox.js 心跳从 25s 缩短至 10s;frontend.html 直连页面此前完全无心跳,新增 10s 应用层心跳。 --- aibox/frontend.html | 10 ++++++++++ static/public/js/aibox.js | 4 ++-- 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/aibox/frontend.html b/aibox/frontend.html index a2c4b64..2c460ca 100644 --- a/aibox/frontend.html +++ b/aibox/frontend.html @@ -1355,6 +1355,8 @@ let reconnectAttempts = 0; const MAX_RECONNECT_ATTEMPTS = 5; let manualDisconnect = false; + let heartbeatTimer = null; + const HEARTBEAT_INTERVAL = 10000; function connectWebSocket() { const wsUrl = document.getElementById('ws-url').value.trim(); @@ -1379,6 +1381,13 @@ reconnectAttempts = 0; updateConnectionStatus(true); showSystemMessage(`✅ WebSocket 连接成功!服务器: ${wsUrl}`); + // 启动心跳保活,防止前置代理空闲超时断连 + if (heartbeatTimer) clearInterval(heartbeatTimer); + heartbeatTimer = setInterval(() => { + if (webSocket.readyState === WebSocket.OPEN) { + webSocket.send(JSON.stringify({ type: 'ping' })); + } + }, HEARTBEAT_INTERVAL); }; webSocket.onmessage = (event) => { @@ -1399,6 +1408,7 @@ webSocket.onclose = (event) => { console.log('WebSocket 断开连接:', event.code, event.reason); + if (heartbeatTimer) { clearInterval(heartbeatTimer); heartbeatTimer = null; } updateConnectionStatus(false); if (!manualDisconnect && reconnectAttempts < MAX_RECONNECT_ATTEMPTS) { diff --git a/static/public/js/aibox.js b/static/public/js/aibox.js index 41c48ba..101b2a8 100644 --- a/static/public/js/aibox.js +++ b/static/public/js/aibox.js @@ -44,8 +44,8 @@ let ws = null; let manualClose = false; /* 手动断开则抑制自动重连 */ let reconnectDelay = RECONNECT_MIN; let reconnectTimer = null; -let heartbeatTimer = null; /* 心跳定时器,25s 发送 ping 保持 WS 连接 */ -const HEARTBEAT_INTERVAL = 25000; /* 心跳间隔(< gateway 30s 空闲超时) */ +let heartbeatTimer = null; /* 心跳定时器,10s 发送 ping 保持 WS 连接 */ +const HEARTBEAT_INTERVAL = 10000; /* 心跳间隔:需低于前置代理(Nginx/CDN)的 proxy_read_timeout */ function startHeartbeat() { stopHeartbeat();