Stop a stuck in-flight flag from silently swallowing every later question

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.
This commit is contained in:
Gmer4Lfe
2026-08-02 18:03:21 -04:00
parent e0925b9d38
commit ae7555a423
+28 -3
View File
@@ -341,10 +341,22 @@
+ `<div class="vv-ai-body">${esc(text)}</div></div>`));
scroll();
}
let pendingTimer = null;
function addPending() {
const n = el(`<div class="vv-ai-msg bot" id="vv-ai-pending"><div class="vv-ai-role">Varaverk</div>`
+ `<div class="vv-ai-pending"><span class="vv-ai-dot"></span><span id="vv-ai-phase">starting…</span></div></div>`);
+ `<div class="vv-ai-pending"><span class="vv-ai-dot"></span>`
+ `<span id="vv-ai-phase">starting…</span>`
+ `<span id="vv-ai-elapsed" style="color:#333;font-family:monospace"></span></div></div>`);
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) {