Skip to content

MCP OAuth

lqdflying edited this page Aug 18, 2026 · 3 revisions

MCP OAuth 2.1 Authentication

ChatHub supports OAuth 2.1 Authorization Code flow with PKCE for MCP plugins. Users only need the MCP server URL — all OAuth metadata is auto-discovered.

Features

  • Auto-discovery — Enter a server URL, click Connect, and the app discovers Client ID, Client Secret, Authorization Endpoint, and Token Endpoint automatically via RFC 9728 (/.well-known/oauth-protected-resource) and RFC 8414 (/.well-known/oauth-authorization-server). Optional dynamic client registration (RFC 7591).
  • Popup flow — Authorization opens in a popup window so the plugin editor stays open with all fields intact. After authorizing, the popup closes and the token status updates to "valid".
  • Server-side token storage — OAuth tokens are stored in PostgreSQL (mcp_oauth_tokens table) and automatically injected into MCP connections by the tRPC router. No manual token management needed. Background conversation generation reuses those stored tokens after you close the tab; see Background Conversation Generation.
  • PKCE — All OAuth flows use S256 PKCE for security.
  • Token lifecycle — Automatic access token injection, refresh token support, and disconnect/revoke.

How It Works

  1. Open Plugin Store → Add Plugin → enter MCP server URL
  2. If the server supports OAuth, the OAuth section appears with a Connect button
  3. Click Connect → the app auto-discovers OAuth endpoints
  4. A popup window opens for the OAuth provider's authorization page
  5. After authorizing, the popup closes → token status shows "valid"
  6. Click Test Connection or Install — tokens are injected automatically

Architecture

Frontend (OAuthConfig.tsx)
 → discoverOAuth (tRPC) → oauthDiscovery.ts (RFC 9728 + RFC 8414)
 → initiateOAuth (tRPC) → oauth.ts (PKCE + state storage)
 → Browser redirect to OAuth provider
 → /oauth/mcp-callback page → oauthCallback (tRPC) → exchangeCodeForTokens

Redirect URI

The OAuth redirect_uri is always:

${window.location.origin}/oauth/mcp-callback

It is derived from window.location.origin at runtime and must match in both the authorization request and token exchange.

Database

OAuth tokens are stored in the mcp_oauth_tokens table. A migration safety net (scripts/migrateServerDB/ensureMcpOAuthTokens.cjs) ensures the table exists on every container startup with CREATE TABLE IF NOT EXISTS.

Clone this wiki locally