Skip to content

Fix Firebase auth on non-primary domains — same-origin authDomain (reverse-proxy /__/auth)

RBAC sequence: independent — an auth-infrastructure fix (cross-domain authDomain), orthogonal to the RBAC enforcement + people tracks. No precede/succeed; parallelisable. See the sequence map in T-022. (Marked by EOP Local Assistance, 2026-06-23.)

Why (escalated from I-002)

p-eop sign-in throws "Unable to save initial state / sessionStorage." Root cause (see ticket I-002): Firebase signInWithRedirect with a cross-domain authDomain (aote-pms.firebaseapp.com) + browser storage partitioning. The sign-in code (app/auth/signin/client.tsx) tries signInWithPopup first, falls back to signInWithRedirect when the popup is blocked (line ~377), and the fallback throws — surfaced to the user via setError. (getRedirectResult is already caught gracefully at line ~424.) Not Cloudflare, not authorized-domains, not the baked NEXT_PUBLIC_APP_URL (the code uses window.location.origin).

Serve Firebase's auth handler first-party so the redirect round-trip stays same-origin: 1. Next.js rewrite: proxy /__/auth/:path*https://aote-pms.firebaseapp.com/__/auth/:path* (and /__/firebase/* if needed) in next.config. 2. authDomain = the app's own domain, baked per branch: NEXT_PUBLIC_FIREBASE_AUTH_DOMAIN = eop.theestablishers.com (main) / p-eop.theestablishers.com (nightly) — add to the per-branch cfg step in .github/workflows/nas-image.yml (alongside NEXT_PUBLIC_APP_URL). 3. eop + p-eop are already Firebase authorized domains (owner-confirmed), so no console change.

Rollout — preview-first (that's what the split is for)

  • Deploy to nightly → p-eop FIRST; test Google sign-in on p-eop (popup and redirect paths).
  • Promote to main/eop only after p-eop sign-in is verified — never risk locking the directors out of prod with an untested authDomain change.
  • Rollback: revert authDomain to aote-pms.firebaseapp.com.

Decision log

2026-06-21 — escalated from ticket I-002

  • Attestation (EOP Local Assistance): read AGENTS.md; opened this as the structural escalation of ticket I-002 (per the Tickets rule — symptom ticket → T-NNN for the structural fix).
  • Source: EOP Local Assistance · session 63c32698-0f80-464c-a668-f352be2c148e (local Claude Code)
  • Proposed by: EOP Local Assistance. Approved by: the owner.
  • Why routed this way: redirect-based Firebase auth can't be fixed by config alone on a self-hosted multi-domain setup; a same-origin authDomain (reverse-proxied handler) is the standard fix. Deployed preview-first because an untested authDomain change risks breaking prod sign-in.
  • Evidence — owner, 2026-06-21 (verbatim):

    "Please also proceed to work on I-002"

2026-06-22 — driver changed: p-eop dropped → now latent PROD hardening (low priority)

  • Source: EOP Local Assistance · session 63c32698-0f80-464c-a668-f352be2c148e (local Claude Code)
  • The immediate driver (the p-eop symptom, I-002) is gone — the owner dropped the NAS preview (T-082), so p-eop no longer exists and I-002 is closed. This task is NOT moot, but its urgency drops sharply.
  • Why keep it open: the same cross-domain authDomain (aote-pms.firebaseapp.com) + signInWithRedirect fragility latently affects prod (eop) — if a director's browser ever blocks the Google sign-in popup, the redirect fallback could throw the same "Unable to save initial state" error and lock them out of prod. The same-origin authDomain fix (above) is cheap insurance against that.
  • Reframed scope: harden eop (prod) auth only — bake authDomain = eop.theestablishers.com for main (drop the per-branch p-eop bit from step 2). Low priority — no active symptom; popup works today. Revisit if a sign-in failure is ever reported on eop, or fold it into the eventual prod→Vercel move (T-082).

2026-07-09 — dropped: driver dead (p-eop retired); remnant folded into T-154

  • ✅ Read AGENTS.md. Outcome/verdict: never started; closing without work commits (no SHAs to list). The task existed to fix sign-in on p-eop (I-002) — that host was retired 2026-06-22 and hosting moved back to Vercel, so the driver no longer exists; production sign-in on eop.theestablishers.com works (popup path). Surviving remnant: the popup-BLOCKED signInWithRedirect fallback still breaks under browser storage partitioning with the cross-domain authDomain — classically iOS Safari — and is now a scoped item inside T-154 (iOS 26 Safari optimization), where the same-origin authDomain / reverse-proxy /__/auth fix from this task's body remains the reference design. Blast radius: none (no code changed). Owner approval (2026-07-09, verbatim): "Do the board hygiene and route T-038, T-040, T-072, T-083, T-051".
  • Source: EOP Local Assistance (fork) · session edb0abc7-6373-449b-8e31-379fd38d391b