rowboat/apps/x/packages
Ramnique Singh 45bdbfcbbc Fix spurious "Reconnect Google" on cold start
When the app launches after the access token has expired, the Gmail and
Calendar sync loops both try to refresh at the same instant. The backend
dedup returns 429 to whichever request arrives second, and we were
treating that 429 as a permanent failure — writing an error into
oauth.json that surfaces in the UI as "Needs reconnect", even though
the tokens are valid and the other refresh succeeded.

Two changes address this:

- GoogleClientFactory now serializes concurrent getClient() callers
  end-to-end, so Gmail and Calendar share a single refresh round-trip
  instead of racing the backend.

- A 429 (or 5xx) from the refresh API is now classified as transient:
  we leave stored tokens and the in-memory cache alone and let the
  next sync tick retry, rather than flagging the user for reconnect.

Refresh logs now include enough detail (time-since-expiry, new TTL,
cause chain on failure) to diagnose the next class of issue from a
single user's log.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-27 02:25:03 +05:30
..
core Fix spurious "Reconnect Google" on cold start 2026-05-27 02:25:03 +05:30
shared Refactor builtin file tools beyond workspace scope 2026-05-25 16:21:51 +05:30