MCP OAuth DCR fails for Calendly: client_name "Claude Code (<server>)" rejected as invalid_client_metadata

Resolved 💬 1 comment Opened May 15, 2026 by blaine-loop Closed Jun 14, 2026

Summary

Connecting the Calendly MCP server (https://mcp.calendly.com/) via OAuth fails during Dynamic Client Registration because Claude Code's hardcoded client_name contains parentheses, which Calendly's /oauth/register endpoint rejects per RFC 7591.

Environment

  • Claude Code version: 2.1.132 (Homebrew, macOS arm64)
  • Server: Calendly MCP — https://mcp.calendly.com/
  • Registered via: claude mcp add --transport http calendly https://mcp.calendly.com/ -s user

Symptom

MCP log shows:

Fetched OAuth metadata with scope: NONE
Saving discovery state (authServer: https://calendly.com/)
No client info found
SDK auth error: GmH
Error during auth completion: Error: SDK auth failed:

(empty error message after the colon). Repeats indefinitely; OAuth browser flow never opens.

Root cause

Claude Code constructs the DCR request body as (from the bundled CLI):

{
  client_name: `Claude Code (${this.serverName})`,
  redirect_uris: [this.redirectUri],
  grant_types: ["authorization_code", "refresh_token"],
  response_types: ["code"],
  token_endpoint_auth_method: "none"
}

For the Calendly server, client_name becomes "Claude Code (calendly)". Calendly's registration endpoint enforces a stricter validation than RFC 7591 requires and rejects parentheses:

$ curl -sS -X POST https://calendly.com/oauth/register \
    -H "Content-Type: application/json" \
    -d '{"client_name":"Claude Code (calendly)","redirect_uris":["http://localhost:51543/callback"],"grant_types":["authorization_code","refresh_token"],"response_types":["code"],"token_endpoint_auth_method":"none"}'

{"error":"invalid_client_metadata","errors":{"name":["may only contain alphanumeric characters, hyphens, and spaces."]}}

Swapping the name to "Claude-Code-calendly" or "claude-code-mcp" succeeds (201 Created).

The error class in the bundled CLI (GmH, errorCode="invalid_client_metadata") is thrown, but the message is dropped before reaching the log — so users only see SDK auth failed: with no detail, making this very hard to diagnose without inspecting the binary.

Repro

  1. claude mcp add --transport http calendly https://mcp.calendly.com/ -s user
  2. Restart Claude Code so it attempts to connect.
  3. Observe ~/Library/Caches/claude-cli-nodejs/*/mcp-logs-calendly/*.jsonl — auth flow fails on every retry with SDK auth error: GmH.

Proposed fixes

  1. Primary: change the hardcoded client_name to a paren-free format, e.g. Claude-Code-${serverName} or just Claude Code ${serverName} (Calendly accepts spaces) — or sanitize parens out at the call site.
  2. Bonus: surface the underlying error from the GmH exception when it's an invalid_client_metadata response. The empty SDK auth failed: message is the main reason this took so long to root-cause; a one-line change to include error_description from the server's response would make this self-diagnosing.

Workaround (for anyone hitting this in the wild)

Pre-register a client manually with a paren-free name, pin the OAuth callback port via MCP_OAUTH_CALLBACK_PORT in ~/.claude/settings.json env, and inject the resulting client_id into the Claude Code-credentials keychain blob under mcpOAuth.<server>|<hash>.clientId (with a matching redirectUri). The SDK's clientInformation() reuses the cached clientId and skips DCR.

View original on GitHub ↗

This issue has 1 comment on GitHub. Read the full discussion on GitHub ↗