Context
Follow-up RCA for #3734 (which only adds observability for this failure).
store_session (src/openhuman/credentials/ops.rs) validates the session JWT via GET /auth/me before persisting the auth profile. If that call fails transiently (timeout / gateway 5xx), the profile is never written, so a successful OAuth bounces the user straight back to the signin page on the next snapshot refresh.
Why it's fragile
- The store-time
/auth/me call has no timeout override and builds a fresh http1_only reqwest client per call (no connection reuse), so it's slow/timeout-prone under contention.
- A single transient failure is treated as fatal — the login is hard-bounced rather than retried or tolerated.
- The session is stored with an empty user (
storeSession(sessionToken, {})), so currentUser can't hydrate from disk when /auth/me is degraded.
Proposed fix (options)
- Don't hard-fail on transient
/auth/me — if the JWT has a valid local exp, persist the profile and revalidate on the next snapshot, instead of returning Err.
- Bounded retry for transient (timeout / 5xx)
/auth/me at store time.
- Pool the
/auth/me client (reuse, drop http1_only) so it stops being a multi-second liability.
- Store the real user (decode from JWT) instead of
{}, and let the post-login commit accept sessionToken + isAuthenticated without requiring currentUser.
Acceptance
A transient /auth/me timeout/5xx during sign-in no longer bounces the user to the login page; the session persists and recovers.
Context
Follow-up RCA for #3734 (which only adds observability for this failure).
store_session(src/openhuman/credentials/ops.rs) validates the session JWT viaGET /auth/mebefore persisting the auth profile. If that call fails transiently (timeout / gateway 5xx), the profile is never written, so a successful OAuth bounces the user straight back to the signin page on the next snapshot refresh.Why it's fragile
/auth/mecall has no timeout override and builds a freshhttp1_onlyreqwest client per call (no connection reuse), so it's slow/timeout-prone under contention.storeSession(sessionToken, {})), socurrentUsercan't hydrate from disk when/auth/meis degraded.Proposed fix (options)
/auth/me— if the JWT has a valid localexp, persist the profile and revalidate on the next snapshot, instead of returningErr./auth/meat store time./auth/meclient (reuse, drophttp1_only) so it stops being a multi-second liability.{}, and let the post-login commit acceptsessionToken + isAuthenticatedwithout requiringcurrentUser.Acceptance
A transient
/auth/metimeout/5xx during sign-in no longer bounces the user to the login page; the session persists and recovers.