Skip to content

fix(tokens): /me/tokens sign-in gate must check /auth/user JSON, not resp.ok - #2071

Merged
jung-thomas merged 1 commit into
DEVfrom
fix/tokens-auth-gate-1093
Aug 28, 2026
Merged

jung-thomas merged 1 commit into
DEVfrom
fix/tokens-auth-gate-1093

Conversation

@jung-thomas

Copy link
Copy Markdown
Contributor

Problem

/me/tokens/ shows "Couldn't load your tokens. Try refreshing." for users whose session has lapsed, instead of a sign-in prompt.

Root cause

The approuter serves an anonymous/expired session as HTTP 200 + an XSUAA login-redirect HTML page (not a 401), and Akamai can serve a cached anon /auth/user to a signed-in browser. The tokens island's onMounted gate checked resp.ok only:

  • resp.ok is true for the 200 login page → needsLogin never set → falls through to loadTokens().
  • loadTokens() then GETs /pats/MyPATs → also 200 + HTML → resp.json() throws → caught → generic load error at ApiTokens.vue:147.

Confirmed live: GET /auth/user and GET /pats/MyPATs on PROD both return HTTP 200 with the login-redirect HTML for an anonymous request.

Same class as prior incidents: island /auth/user probes must check JSON + body.authenticated, not r.ok (#1093 homepage-personalizer fix).

Fix

  • isSignedIn() gate: require ok + JSON content-type + body.authenticated (mirrors homepage-personalizer/coordinator.ts).
  • Harden loadTokens(): a non-JSON 200 (session lapsed mid-flow) falls back to the sign-in prompt, not the load error.
  • Regression tests: 200+HTML on /auth/user and /pats/MyPATs, plus authenticated:false.

Test

npx vitest run --project unit hugo-apps/src/tokens → 8 passed.

The approuter serves a lapsed/anonymous session as HTTP 200 + an XSUAA
login-redirect HTML page (not 401), and Akamai can serve a cached anon
/auth/user to a signed-in browser. The /me/tokens island gated on
resp.ok alone, so it never set needsLogin, fell through to loadTokens(),
and resp.json() threw on the HTML body -> the page showed
"Couldn't load your tokens. Try refreshing." instead of a sign-in prompt.

- Gate via isSignedIn(): require ok + JSON content-type + body.authenticated
  (mirrors homepage-personalizer/coordinator.ts).
- Harden loadTokens(): a non-JSON 200 (HTML login page) now falls back to
  the sign-in prompt, not the generic load error.
- Add regression tests for 200+HTML on /auth/user and /pats/MyPATs, and
  authenticated:false.
@jung-thomas
jung-thomas merged commit 024baa4 into DEV Aug 28, 2026
3 of 4 checks passed
@jung-thomas
jung-thomas deleted the fix/tokens-auth-gate-1093 branch August 28, 2026 14:34
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.

1 participant