From ae7555a423955326884dbcfa757f324b6e1c3863 Mon Sep 17 00:00:00 2001 From: Gmer4Lfe Date: Sun, 2 Aug 2026 18:03:21 -0400 Subject: [PATCH] Stop a stuck in-flight flag from silently swallowing every later question MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A turn that ended without finish() left busy=true, so send() returned at line one for every subsequent click — no fetch, no error, and the original "starting…" still on screen. That is a hang which produces no request and so no server-side trace of any kind. It now says what happened, and the pending indicator carries an elapsed counter so stalled and merely slow look different. --- Plugin/unraid/pages/ai.php | 31 ++++++++++++++++++++++++++++--- 1 file changed, 28 insertions(+), 3 deletions(-) diff --git a/Plugin/unraid/pages/ai.php b/Plugin/unraid/pages/ai.php index 1410962..18a7394 100644 --- a/Plugin/unraid/pages/ai.php +++ b/Plugin/unraid/pages/ai.php @@ -341,10 +341,22 @@ + `
${esc(text)}
`)); scroll(); } + let pendingTimer = null; function addPending() { const n = el(`
Varaverk
` - + `
starting…
`); + + `
` + + `starting…` + + `
`); chat().appendChild(n); scroll(); + // An elapsed counter distinguishes "working" from "wedged" at a glance. Without it a stalled + // turn and a slow one look identical, and the slow case here is legitimately ~40s. + const t0 = Date.now(); + clearInterval(pendingTimer); + pendingTimer = setInterval(() => { + const e = $('vv-ai-elapsed'); + if (!e) { clearInterval(pendingTimer); return; } + e.textContent = Math.round((Date.now() - t0) / 1000) + 's'; + }, 1000); } function phase(t) { const p = $('vv-ai-phase'); if (p) p.textContent = t; } @@ -389,7 +401,16 @@ // ── Ask / poll ────────────────────────────────────────────────────────── function send() { - if (busy) return; + // Never fail silently on a stuck flag. A turn that ends without finish() — a throw, a poll + // loop that stopped, a tab left open across a deploy — would otherwise make every later + // click a no-op with the previous "starting…" still on screen, which reads as a hang that + // produces no request and therefore no server-side trace at all. That cost a diagnosis + // session; it now says so and offers the way out. + if (busy) { + addError('A previous question is still marked in-flight, so this one was not sent. ' + + 'Reload the tab to reset it.'); + return; + } const q = $('vv-ai-input').value.trim(); if (!q) return; @@ -439,7 +460,11 @@ .catch(e => { addError('Request failed: ' + (e && e.message ? e.message : e)); finish(); }); } - function finish() { busy = false; $('vv-ai-send').disabled = false; } + function finish() { + busy = false; + $('vv-ai-send').disabled = false; + clearInterval(pendingTimer); + } function poll(token, started) { if (Date.now() - started > POLL_CEIL) {