Skip to content

fix: restore OAuth token expiry across process restarts - #3248

Open
dhruvkej9 wants to merge 2 commits into
modelcontextprotocol:mainfrom
dhruvkej9:fix/restore-token-expiry-on-init
Open

fix: restore OAuth token expiry across process restarts#3248
dhruvkej9 wants to merge 2 commits into
modelcontextprotocol:mainfrom
dhruvkej9:fix/restore-token-expiry-on-init

Conversation

@dhruvkej9

@dhruvkej9 dhruvkej9 commented Aug 4, 2026

Copy link
Copy Markdown

Problem

OAuthClientProvider._initialize (and the client-credentials providers) reloads current_tokens from storage but never restores token_expiry_time. The persisted OAuthToken only carries the relative expires_in, so on a fresh process is_token_valid() returns True for an already-expired access token — a stale Bearer is sent and a 401 round-trip is wasted before re-authentication (mcp2cli issues #50, #57).

Fix

Persist the absolute expiry and restore it on init:

  • Add expires_at: float | None to OAuthToken (absolute unix timestamp), with a doc comment explaining the mcp2cli reproduction that motivated it.
  • Set it when tokens are stored (_handle_token_response, _handle_refresh_response).
  • Add OAuthContext.restore_token_expiry() and call it from all three _initialize methods (base, ClientCredentialsOAuthProvider, PrivateKeyJwtOAuthProvider).

Backwards compatible: expires_at defaults to None; existing stored tokens simply re-auth once, then persist the absolute expiry going forward.

Test

test_init_restores_expired_token_expiry — fails on main (expired token reported valid), passes with the fix. 210 auth tests pass, ruff + pyright clean.

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No issues found across 4 files

Re-trigger cubic

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