fix(portal): 客服浮窗轮询参数调整,压感知延迟并留足超时预算

现象:访客在公开页问客服,等约 9.5 秒后报「客服响应超时」。
根因不在链路快慢 —— Agent Worker 没在跑,run 一直停在 queued,
前端把「没人处理」呈现成了「超时」。

启动 Worker 后实测同一条链路(受理 0.05s + 意图分类 + 知识检索 + 落库):
4.11s / 4.09s / 4.82s,三条全部 succeeded。模型已经是 deepseek-flash,
延迟主要来自一次意图分类加一次 embedding,不是模型选型问题。

不过原来的轮询参数余量确实偏薄:350ms 后首次、之后每 700ms 一次、共 14 次,
约 9.5 秒封顶,后端稍一抖动就撞上;而且平均要多等半个轮询周期才看到结果。
改为 300ms 后首次、之后每 500ms 一次、共 40 次(约 20 秒):
感知延迟压到半秒内,同时给模型与检索抖动留出余量。
超时文案也从「客服响应超时,请稍后重试」改为「客服繁忙,暂时没能给出答复」,
不再暗示是响应慢。代码注释里写明:若仍然超时,先确认 Agent Worker 已启动。
This commit is contained in:
2026-09-13 19:03:49 +08:00
parent d4a895c643
commit 2098185477
@@ -101,14 +101,21 @@ export function mountCustomerServiceWidget(mode = 'public') {
return sessionId;
}
async function waitForRun(runId) {
for (let attempt = 0; attempt < 14; attempt += 1) {
await new Promise((resolve) => window.setTimeout(resolve, attempt ? 700 : 350));
// 实测(本机 + DeepSeek):整条链路「受理 0.05s + 意图分类 + 知识检索 + 落库」
// 约 4.1–4.8 秒。原参数是「350ms 后首次、之后每 700ms 一次、共 14 次」≈ 9.5 秒封顶,
// 后端稍一抖动就撞上限;而且平均要多等半个轮询周期(350ms)才看到结果。
// 改为「300ms 后首次、之后每 500ms 一次、共 40 次」≈ 20 秒:感知延迟压到半秒内,
// 同时给模型/检索抖动留出余量。
// ⚠️ 若这里仍然超时,先确认 Agent Worker 已启动(`python -m app.worker`)——
// 没有 Worker 时 run 会一直停在 queued,任何轮询预算都不够。
for (let attempt = 0; attempt < 40; attempt += 1) {
await new Promise((resolve) => window.setTimeout(resolve, attempt ? 500 : 300));
const response = await apiClient.get('R002', { pathParams: { runId }, headers: authHeaders() });
const snapshot = response.data || {};
if (snapshot.status === 'succeeded') return snapshot.result?.reply || snapshot.result?.content || '暂时没有可展示的回复。';
if (snapshot.status === 'failed' || snapshot.status === 'cancelled') throw new ApiError('客服暂时无法完成回答,请稍后重试。');
}
throw new ApiError('客服响应超时,请稍后重试。');
throw new ApiError('客服繁忙,暂时没能给出答复,请稍后重试。');
}
form.addEventListener('submit', async (event) => {
event.preventDefault();