# Client setup

> Config for Claude Code, the Claude chat apps, Gemini CLI, Antigravity, Codex CLI, Cursor, VS Code, and anything else.

Find your client and note the field name it expects - three different keys are in use for the same URL.

<Warning>
  **The Claude chat apps (claude.ai and Claude Desktop) are not recommended** - no file uploads, no image scanning. Prefer **Claude Code**, which is fully capable in every form including its desktop app.
</Warning>

| Client | Config file | URL field | Auth |
|---|---|---|---|
| **Claude Code** | `.mcp.json` / `~/.claude.json` | `url` + `"type":"http"` | Built-in OAuth |
| **Claude Desktop** | UI only - Connectors | URL field in dialog | Built-in OAuth |
| **Gemini CLI** | `~/.gemini/settings.json` | `httpUrl` | Built-in OAuth |
| **Antigravity** | `~/.gemini/config/mcp_config.json` | `serverUrl` | Built-in OAuth |
| **Codex CLI** | `~/.codex/config.toml` | `url` | Built-in OAuth |
| **Cursor** | `~/.cursor/mcp.json` | `url` | Built-in OAuth |
| **VS Code** (Copilot) | `.vscode/mcp.json` | `url`, under `servers` | Built-in OAuth |
| **Other clients** | whatever it uses for stdio | `command` → `mcp-remote` | Via bridge |

<Note>
  **After adding the server, start a new session.** Clients read their server list at startup, so a server added mid-conversation will not appear. Restart the CLI, or quit and reopen the desktop app - closing the window is not enough.
</Note>

<Tabs>

<Tab title="Claude Code">

Add the server. Use `--scope user` so it follows you into every project; drop the flag to keep it to the current directory.

```bash title="Add the server" icon="terminal"
claude mcp add --transport http copyleaks_app --scope user https://extensions.copyleaks.com/mcp
```

Start Claude Code, run `/mcp`, pick **copyleaks_app**, and sign in. The browser round-trip stores a token in your OS keychain - you will not be asked again until it expires.

Or sign in without a session: `claude mcp login copyleaks_app`. If the browser does not open, open the printed URL yourself. On a headless machine or over SSH, add `--no-browser` and paste the full redirect URL back at the prompt - over SSH, connect with `ssh -t` so the paste prompt works.

Confirm:

```bash title="Check the connection" icon="terminal"
claude mcp list
claude mcp get copyleaks_app
```

A healthy server reports **✔ Connected**. **! Needs authentication** means the sign-in did not complete. **⏸ Pending approval** means a committed `.mcp.json` entry has not been approved on this machine yet - run `/mcp` and approve it.

**Sharing it with a team** - add it to `.mcp.json` at the project root and commit that file. Each teammate approves the server once and signs in with their own Copyleaks account; no credentials travel in the file.

```json title=".mcp.json"
{
  "mcpServers": {
    "copyleaks_app": {
      "type": "http",
      "url": "https://extensions.copyleaks.com/mcp"
    }
  }
}
```

<Warning>
  **A `url` with no `type` is silently skipped.** A JSON entry with a `url` and no `type` is read as a local command and skipped, with the message `MCP server "copyleaks_app" has a "url" but no "type"`. Config blocks written for other clients routinely omit it. **Always add `"type": "http"`.**
</Warning>

</Tab>

<Tab title="Claude Desktop and claude.ai">

<Note>
  Setting up **Claude Code**, including its desktop app, is the **Claude Code** tab.
</Note>

Claude Desktop reaches remote MCP servers as **custom connectors**. There is no `claude_desktop_config.json` entry for this - that file handles locally installed servers only.

<Steps>
  <Step title="Open the connector settings">
    Go to **Settings → Customize → Connectors**.
  </Step>
  <Step title="Add a custom connector">
    Press **+**, then **Add custom connector**.
  </Step>
  <Step title="Paste the endpoint">
    Paste `https://extensions.copyleaks.com/mcp` and leave **Advanced settings** untouched - the server registers the client for you.
  </Step>
  <Step title="Connect">
    Press **Add**, then **Connect**, and approve the permissions the sign-in page requests.
  </Step>
</Steps>

Connectors are held against your Claude account, so adding it on the web also makes it available in Claude Desktop.

<Warning>
  **Not recommended - use Claude Code instead.**

  **The Claude chat apps are the most limited way to use Copyleaks.** They cannot send a file to an upload address, which means **files larger than a small one will not scan, and image scanning does not work at all** - see [Scanning](/mcp/scanning).

  What still works: pasted text, web pages, reading results, searching past scans, and scan profiles. If that is genuinely all you need, they are fine - and they accept larger single replies than any other Claude client.

  **For everything else, use Claude Code.** It is fully capable in all four of its forms - terminal, **desktop app**, web, and IDE extension.

  **Two different products share the word "desktop".** Claude Code's desktop app is not Claude Desktop: Claude Desktop is the Claude *chat* app, and one of the two limited surfaces here.
</Warning>

<Note>
  **Team and Enterprise workspaces** - an Owner adds the connector once under **Organization settings → Connectors**. Every member then connects it from their own **Customize → Connectors** and signs in as themselves. The organization-level entry publishes the server; it does not share a session or a Copyleaks account.
</Note>

</Tab>

<Tab title="Gemini CLI">

```bash title="Add the server" icon="terminal"
gemini mcp add --transport http --scope user copyleaks_app https://extensions.copyleaks.com/mcp
```

Or write it into `~/.gemini/settings.json` (user scope) or `.gemini/settings.json` (project scope), which also lets you name the permissions you want and set a timeout:

```json title="~/.gemini/settings.json"
{
  "mcpServers": {
    "copyleaks_app": {
      "httpUrl": "https://extensions.copyleaks.com/mcp",
      "oauth": {
        "enabled": true,
        "scopes": ["scans:read", "scans:run", "profiles:read", "profiles:write", "account:read", "offline_access"]
      },
      "timeout": 30000
    }
  }
}
```

<Warning>
  **`httpUrl`, not `url`.** In Gemini CLI, `url` means SSE and `httpUrl` means Streamable HTTP. Using `url` here makes the client open an SSE connection the server does not serve, and the failure looks like a network problem rather than a config mistake.
</Warning>

Verify inside the CLI with `/mcp`, which lists each server, its status, and the tools it exposes. Add `--trust` at add-time only if you want to skip per-call tool confirmations - it removes them for write operations too, so reserve it for read-only permission sets.

</Tab>

<Tab title="Antigravity">

Antigravity keeps MCP configuration in `mcp_config.json` - globally at `~/.gemini/config/mcp_config.json`, or per-project at `.agents/mcp_config.json`. Remote servers use `serverUrl` for both Streamable HTTP and SSE; the client works out which by talking to the endpoint.

```json title="mcp_config.json"
{
  "mcpServers": {
    "copyleaks_app": {
      "serverUrl": "https://extensions.copyleaks.com/mcp"
    }
  }
}
```

<Warning>
  **Legacy fields are rejected.** Antigravity does not accept `url` or `httpUrl`. Pasting a Gemini CLI or Cursor block straight in will not connect. **Rename the key to `serverUrl`.**
</Warning>

Antigravity supports OAuth with dynamic client registration. Use `disabled: true` to park the server without deleting it, and `disabledTools` to hide individual tools from the model.

</Tab>

<Tab title="Codex CLI">

Codex reads MCP servers from `~/.codex/config.toml`. The table key becomes the server name, so use underscores rather than hyphens.

```toml title="~/.codex/config.toml"
[mcp_servers.copyleaks_app]
url = "https://extensions.copyleaks.com/mcp"
auth = "oauth"
scopes = ["scans:read", "scans:run", "profiles:read", "profiles:write", "account:read", "offline_access"]
startup_timeout_sec = 30
tool_timeout_sec = 120
```

Then complete the sign-in once:

```bash title="Sign in" icon="terminal"
codex mcp login copyleaks_app
```

Useful per-server controls: `enabled` to toggle without deleting, `required = true` to fail startup if the server is unreachable, `enabled_tools` / `disabled_tools` to narrow the surface, and `default_tools_approval_mode` to decide what runs without a prompt.

<Tip>
  Codex accepts the smallest tool replies of any client listed here. On a document with very many matched sources, ask for a narrower view - one match type, one source type, or a minimum matched-word count - rather than everything at once.
</Tip>

</Tab>

<Tab title="Cursor and VS Code">

Cursor infers the transport from the URL, so a remote server needs nothing but the address:

```json title="~/.cursor/mcp.json"
{
  "mcpServers": {
    "copyleaks_app": {
      "url": "https://extensions.copyleaks.com/mcp"
    }
  }
}
```

Global config lives at `~/.cursor/mcp.json`, per-project at `.cursor/mcp.json`. Cursor completes OAuth in the browser using fixed redirect URLs - `http://localhost:8787/callback` on the desktop app, `https://www.cursor.com/agents/mcp/oauth/callback` for web agents.

**VS Code with GitHub Copilot** follows the same shape in `.vscode/mcp.json`, under a `servers` key rather than `mcpServers`. Add the server through **MCP: Add Server → HTTP** and let the editor write the file, which avoids guessing the current schema.

</Tab>

<Tab title="Anything else">

Plenty of MCP clients still speak only stdio. Bridge them with `mcp-remote`, which runs locally, handles the OAuth sign-in in your browser, and proxies the session to the remote endpoint. Any client that can launch a command can use it.

```json title="Bridged with mcp-remote"
{
  "mcpServers": {
    "copyleaks_app": {
      "command": "npx",
      "args": ["-y", "mcp-remote", "https://extensions.copyleaks.com/mcp"]
    }
  }
}
```

<Note>
  Treat the bridge as a compatibility shim, not a default. It adds a Node process per client, caches its own tokens on disk under `~/.mcp-auth`, and its failures are harder to read than a native connection's.
</Note>

</Tab>

</Tabs>

<Card title="Verify the connection" icon="circle-check" href="/mcp/verify">
  Probe the endpoint from your own machine before blaming a client.
</Card>
