docs/clients/auth/cimd.mdx
import { VersionBadge } from "/snippets/version-badge.mdx"
<VersionBadge version="3.0.0" /> <Tip> CIMD authentication is only relevant for HTTP-based transports and requires a server that advertises CIMD support. </Tip>With standard OAuth, your client registers dynamically with every server it connects to, receiving a fresh client_id each time. This works, but the server has no way to verify who your client actually is — any client can claim any name during registration.
CIMD (Client ID Metadata Documents) flips this around. You host a small JSON document at an HTTPS URL you control, and that URL becomes your client_id. When your client connects to a server, the server fetches your metadata document and can verify your identity through your domain ownership. Users see a verified domain badge in the consent screen instead of an unverified client name.
Pass your CIMD document URL to the client_metadata_url parameter of OAuth:
from fastmcp import Client
from fastmcp.client.auth import OAuth
async with Client(
"https://mcp-server.example.com/mcp",
auth=OAuth(
client_metadata_url="https://myapp.example.com/oauth/client.json",
),
) as client:
await client.ping()
When the server supports CIMD, the client uses your metadata URL as its client_id instead of performing Dynamic Client Registration. The server fetches your document, validates it, and proceeds with the standard OAuth authorization flow.
A CIMD document is a JSON file that describes your client. The most important field is client_id, which must exactly match the URL where you host the document.
Use the FastMCP CLI to generate one:
fastmcp auth cimd create \
--name "My Application" \
--redirect-uri "http://localhost:*/callback" \
--client-id "https://myapp.example.com/oauth/client.json"
This produces:
{
"client_id": "https://myapp.example.com/oauth/client.json",
"client_name": "My Application",
"redirect_uris": ["http://localhost:*/callback"],
"token_endpoint_auth_method": "none",
"grant_types": ["authorization_code"],
"response_types": ["code"]
}
If you omit --client-id, the CLI generates a placeholder value and reminds you to update it before hosting.
The create command accepts these flags:
| Flag | Description |
|---|---|
--name | Human-readable client name (required) |
--redirect-uri, -r | Allowed redirect URIs — can be specified multiple times (required) |
--client-id | The URL where you'll host this document (sets client_id directly) |
--output, -o | Write to a file instead of stdout |
--scope | Space-separated list of scopes the client may request |
--client-uri | URL of the client's home page |
--logo-uri | URL of the client's logo image |
--no-pretty | Output compact JSON |
The redirect_uris field supports wildcard port matching for localhost. The pattern http://localhost:*/callback matches any port, which is useful for development clients that bind to random available ports (which is what FastMCP's OAuth helper does by default).
CIMD documents must be hosted at a publicly accessible HTTPS URL with a non-root path:
/oauth/client.json, not just /)client_id — The client_id field in the document must exactly match the hosting URLCommon hosting options include static file hosting services like GitHub Pages, Cloudflare Pages, Vercel, or S3 — anywhere you can serve a JSON file over HTTPS.
Before deploying, verify your hosted document passes validation:
fastmcp auth cimd validate https://myapp.example.com/oauth/client.json
The validator fetches the document and checks that:
client_id in the document matches the URL it was fetched fromWhen your client connects to a CIMD-enabled server, the flow works like this:
<Steps> <Step title="Client Presents Metadata URL"> Your client sends its `client_metadata_url` as the `client_id` in the OAuth authorization request. </Step> <Step title="Server Recognizes CIMD URL"> The server sees that the `client_id` is an HTTPS URL with a path — the signature of a CIMD client — and skips Dynamic Client Registration. </Step> <Step title="Server Fetches and Validates"> The server fetches your JSON document from the URL, validates that `client_id` matches the URL, and extracts your client metadata (name, redirect URIs, scopes). </Step> <Step title="Authorization Proceeds"> The standard OAuth flow continues: browser opens for user consent, authorization code exchange, token issuance. The consent screen shows your verified domain. </Step> </Steps>The server caches your CIMD document according to HTTP cache headers, so subsequent requests don't require re-fetching.
CIMD is a server-side feature that your MCP server must support. FastMCP's OAuth proxy providers (GitHub, Google, Auth0, etc.) support CIMD by default. See the OAuth Proxy CIMD documentation for server-side configuration, including private key JWT authentication and security details.