# Authentication

API keys and connected apps (OAuth sign-in), what each is for, how to send them and where to revoke them.

Every call to a tool needs a credential, and the account behind it needs an active Fundalyze plan or trial. There are two kinds of credential. Both work for the MCP server and the REST API, both only read data, and both are sent the same way:

```http title="Header"
Authorization: Bearer <credential>
```

The tool catalogue (`/tools`), the data dictionary (`/dictionary`) and the OpenAPI document (`/openapi.json`) need no credential.

## API keys

For anything where you paste a token: Claude Code, Cursor, scripts, notebooks, your own server.

- **Create** one in [Account → API & MCP](/account/api). Give it a name you will recognise later ("laptop", "research notebook").
- **It is shown once**, when you create it. Fundalyze keeps only a fingerprint of it, so a lost key cannot be shown again: revoke it and create another.
- A key looks like `fdz_live_` followed by 43 letters and digits. The account page shows its first characters and last four so you can tell keys apart.
- Up to **3 active keys** per account.
- **Revoke** a key from the same page. It stops working at once.

## Connected apps (OAuth sign-in)

For assistants that can sign in on your behalf: Claude Desktop and claude.ai, ChatGPT, and other MCP clients that support OAuth. You never handle a key:

1. You give the app the server address, `https://api.fundalyze.ai/mcp`.
2. The app opens Fundalyze's sign-in page; you sign in with your Fundalyze account and choose **Allow**.
3. The app receives tokens and refreshes them itself.

The access is read-only (scope `read`): an app can call the tools, nothing else. It cannot see or change your highlights, watchlists or billing.

Each connection has its own daily quota and its own one-call-at-a-time limit, separate from your keys. **Disconnect** it in [Account → API & MCP](/account/api) → **Connected apps**: every token of that connection stops working at once, and the app has to ask again.

## Keep credentials secret

- Never put a key in code that runs in a browser or a mobile app, in a public repository, or in a file you share. Use an environment variable or a secrets manager.
- Do not share a key with other people. Anything done with your key counts as done by you ([Terms](/terms#api)).
- If a key may have leaked, revoke it and create a new one. Your usage page shows which key made which calls.

## For client developers: the OAuth details

Fundalyze is its own OAuth 2.1 authorization server. A standards-following MCP client discovers all of this from the server's `401` response; the table is for anyone building or debugging a client.

| What | Where |
|---|---|
| Protected resource metadata (RFC 9728) | `https://api.fundalyze.ai/.well-known/oauth-protected-resource/mcp` |
| Authorization server metadata (RFC 8414) | `https://api.fundalyze.ai/.well-known/oauth-authorization-server` |
| Issuer | `https://api.fundalyze.ai` |
| Dynamic client registration (RFC 7591) | `POST https://api.fundalyze.ai/oauth/register` |
| Authorization endpoint (the consent page) | `https://app.fundalyze.ai/oauth/authorize` |
| Token endpoint | `POST https://api.fundalyze.ai/oauth/token` |
| Revocation (RFC 7009) | `POST https://api.fundalyze.ai/oauth/revoke` |

- **Grants:** authorization code with PKCE (`S256` only), and refresh token. Response type `code`, scope `read`, resource `https://api.fundalyze.ai/mcp`.
- **Client authentication:** `none` (a public client using PKCE) or `client_secret_post`.
- **Redirect URIs:** `https` only, or `http` on `localhost` / `127.0.0.1` for local development. Custom schemes are refused.
- **Tokens:** opaque strings. Access tokens start `fdz_at_` and last one hour; refresh tokens start `fdz_rt_`, last 30 days and are replaced on every use (the old one stops working). Reusing an old refresh token or an authorization code revokes the whole connection.
- **Registration** is limited to 10 new clients an hour from one address.
- An access token works on the REST API too, with the same quota as its connection.
