Skip to content

fix: detect revoked GitHub token immediately instead of waiting up to 24 hours#2873

Open
Tanisha-sharma7302 wants to merge 2 commits into
Priyanshu-byte-coder:mainfrom
Tanisha-sharma7302:fix/oauth-token-expiry-2842
Open

fix: detect revoked GitHub token immediately instead of waiting up to 24 hours#2873
Tanisha-sharma7302 wants to merge 2 commits into
Priyanshu-byte-coder:mainfrom
Tanisha-sharma7302:fix/oauth-token-expiry-2842

Conversation

@Tanisha-sharma7302

Copy link
Copy Markdown

Fixes #2842

Problem

The dashboard only re-validated the stored GitHub OAuth token once every
24 hours (TOKEN_VALIDATION_INTERVAL_MS in auth.ts). If a user revoked
the app's access in GitHub Settings, the app wouldn't notice until the next
scheduled check — for up to 24 hours. In the meantime, every GitHub API call
silently failed with 401, but the dashboard had no way to tell this apart
from a generic network error, so it just showed stale data or a confusing
error instead of prompting the user to reconnect.

The existing TokenRevokedBanner in dashboard/layout.tsx and the
window.fetch 401-interceptor were already built to show a "reconnect"
prompt — but they only fire when session.error === "TokenRevoked", which
was only ever set by the slow 24-hour periodic check.

Fix

Added a fast path so a live 401 from GitHub immediately flags the token
as revoked, instead of waiting for the periodic check:

  • src/lib/token-revocation-flag.ts (new) — markTokenRevokedNow() /
    wasTokenRevokedNow(), backed by the existing Redis cache with a
    short TTL.
  • src/lib/github-fetch.ts — when any GitHub API call returns a live
    401, it now calls markTokenRevokedNow() for that user.
  • src/lib/auth.ts — the NextAuth jwt callback now checks
    wasTokenRevokedNow() on every request. If true, it sets
    session.error = "TokenRevoked" immediately, instead of relying solely
    on the 24-hour periodic check.

This means the existing TokenRevokedBanner ("Your GitHub session has
expired. Please sign out and sign back in to refresh your data.") now
shows up right away on the next page load after revocation, rather than
up to a day later. The original 24-hour periodic check is left in place
as a fallback for routes that don't actively call GitHub.

Testing

  • pnpm run type-check passes with no errors
  • No existing tests were broken

@github-actions github-actions Bot added gssoc26 GSSoC 2026 contribution type:bug GSSoC type bonus: bug fix type:feature GSSoC type bonus: new feature type:performance GSSoC type bonus: performance (+15 pts) labels Jun 27, 2026
@github-actions

Copy link
Copy Markdown

GSSoC Label Checklist 🏷️

@Priyanshu-byte-coder — please apply the appropriate labels before merging:

Difficulty (pick one):

  • level:beginner — 20 pts
  • level:intermediate — 35 pts
  • level:advanced — 55 pts
  • level:critical — 80 pts

Quality (optional):

  • quality:clean — ×1.2 multiplier
  • quality:exceptional — ×1.5 multiplier

Validation (required to score):

  • gssoc:approved — counts for points
  • gssoc:invalid / gssoc:spam / gssoc:ai-slop — does not score

Type labels (type:*) are auto-detected from files and title. Review and adjust if needed.
Points formula: (difficulty × quality_multiplier) + type_bonus

@github-actions github-actions Bot added the type:testing GSSoC type bonus: tests (+10 pts) label Jun 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

gssoc26 GSSoC 2026 contribution type:bug GSSoC type bonus: bug fix type:feature GSSoC type bonus: new feature type:performance GSSoC type bonus: performance (+15 pts) type:testing GSSoC type bonus: tests (+10 pts)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[BUG] GitHub OAuth access token expiry is not checked before API calls, causing silent 401 failures after token refresh

1 participant