Skip to content

Repair Prometheus JSON + in-place re-login modal - #27

Merged
mbmorote merged 3 commits into
masterfrom
issues-14-12
Aug 28, 2026
Merged

Repair Prometheus JSON + in-place re-login modal#27
mbmorote merged 3 commits into
masterfrom
issues-14-12

Conversation

@mbmorote

Copy link
Copy Markdown
Owner

Summary

  • Repair near-miss JSON in Prometheus responses + surface recovery warnings #12repairNearMissJson() fixes invalid backslash escapes and unescaped control characters inside Prometheus's JSON string literals before the existing 3-attempt parse cascade runs; a recovery warning now surfaces whenever anything past a clean first parse was needed (repair, fence-strip, or slice), including for modifications-less turns where the proposal card never mounts to show it.
  • In-place re-login modal on session expiry #14apiFetch no longer hard-navigates to /login immediately on a 401. It shows an in-place re-auth modal (reusing LoginForm's existing embedded mode) and, on successful password re-auth, retries the original request and resumes in place — a chat send actually completes, not just avoids losing the draft. Concurrent 401s share one prompt. Cancel, or a retry still 401, falls back to the old hard-navigate.
  • Invite-codes table layout — follow-up polish after live testing: one line per row (truncate + tooltip for free-text columns, overflow-x-auto instead of clipping), Revoke moved to the first column, and a compact DD/MM hh:mm date format for this table's Created/Redeemed columns.

Known gap, filed separately as #26 (not fixed here): the modal's "Continue with Google" path signs back in but does not resume the in-flight action (OAuth is a full-page redirect round trip) and currently lands on the default agent rather than the page the user was on. Reproduced live.

Test plan

  • Live-tested in Chrome: cleared the session cookie mid-page (no navigation), sent a chat message, confirmed the re-auth modal appeared in place
  • Signed back in with password — confirmed the original message was actually resent and completed (dry-run response shown for it), not just re-enabled
  • Cancelled the modal — confirmed fallback to hard-navigate /login?next=...
  • Reproduced the Google OAuth gap live (empty chat, wrong agent) — tracked as Re-auth modal: Google sign-in doesn't resume in place (and lands on home, not the original page) #26
  • Prometheus repair-pass/recovery-warning unit tests added; not run in this session (ask-first policy on this repo) — worth a npx vitest run lib/ai/__tests__/prometheus.test.ts lib/__tests__/apiFetch.test.ts pass before merge if you want CI to be the first runner

Closes #12
Closes #14

🤖 Generated with Claude Code

https://claude.ai/code/session_011GYBpuCrvmUzNCGcFABRGw

mbmorote and others added 3 commits August 28, 2026 11:55
A stray backslash (e.g. an unescaped Windows path) in a Prometheus reply
failed all three JSON-extraction attempts and dumped the raw envelope
into the chat bubble. repairNearMissJson() now fixes invalid escapes and
unescaped control characters inside strings before extraction runs, and
a recovery warning is pushed whenever anything past a clean first parse
was needed. ChatPanel now renders that warning for modifications-less
turns too, where the proposal card never mounts to show it.

Closes #12

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_011GYBpuCrvmUzNCGcFABRGw
apiFetch previously hard-navigated to /login on any 401, discarding
unsaved state (a half-typed chat message, an in-progress edit). It now
shows a re-auth modal (reusing LoginForm's existing embedded mode) and,
on successful re-auth, retries the original request and resumes in
place instead of just avoiding navigation. Concurrent 401s share one
prompt. A cancelled re-auth, or a retry still 401, falls back to the
old hard-navigate behavior. Mounted once at the root layout so it
covers every apiFetch call site.

Closes #14

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_011GYBpuCrvmUzNCGcFABRGw
Label and For were unbounded free text that could wrap a row across
several lines, and the Code column's Copy button could get clipped by
the panel's overflow-hidden. Truncates Label/For at 110px with a hover
tooltip for the full value, marks the remaining short/bounded columns
whitespace-nowrap, wraps the table in its own overflow-x-auto scroll
container instead of relying on the panel's clipping overflow, and
reorders columns (Revoke, Code, For, Created, Expires, Status, Label)
per live iteration against the running table. Created (and a redeemed
row's "Redeemed ..." timestamp) now render as a local DD/MM hh:mm
format specific to this table, not a change to prefsShared.tsx's
shared formatTs() used elsewhere.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_011GYBpuCrvmUzNCGcFABRGw
@mbmorote
mbmorote merged commit 8657dba into master Aug 28, 2026
2 checks passed
@mbmorote
mbmorote deleted the issues-14-12 branch August 31, 2026 21:28
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

In-place re-login modal on session expiry Repair near-miss JSON in Prometheus responses + surface recovery warnings

1 participant