Docs · Claude setup

Claude LinkedIn MCP: the install

Yes — Claude can drive LinkedIn outreach through MCP. Here is the server, the exact config, and a first call that returns real data. Roughly five minutes if the workspace already has an account connected.

Endpointhttps://topclozer.com/api/mcp

Updated 2026-09-10 · Protocol 2025-06-18 · Transport: HTTP JSON-RPC

The 30-second version

  1. 1. A LinkedIn account connected to the workspace — not your personal profile.
  2. 2. An API key from Developer.
  3. 3. claude mcp add --transport http topclozer https://topclozer.com/api/mcp --header "Authorization: Bearer …"
  4. 4. Ask Claude: "list my TopClozer campaigns".

Step 0 — an account for the agent to act as

This is a real prerequisite, not an upsell, and it is where most agent-driven LinkedIn projects come apart. The MCP tools operate a TopClozer workspace; the workspace sends from a connected LinkedIn account. Automating your own profile is against LinkedIn's User Agreement, and a restricted personal profile costs you your network, not just a campaign.

So teams put a separate account behind the automation. We do not sell accounts — the two honest routes are renting a managed verified account, which is the shorter path because it arrives warmed and gets replaced if it goes down, or buying an aged account if you would rather own it. The comparison, and what an agent-driveable account actually needs, is on accounts for agents.

You can install first

The MCP connection works with an empty workspace — the read tools simply return empty arrays. Wire Claude up, confirm the handshake, then connect the account.

Step 1 — get an API key

In the app: Developer → Create a key (MCP). The key starts with tcz_live_ and is shown exactly once — we store only its SHA-256, so it cannot be re-displayed, by you or by us. Copy it into your client's config right away. Lost it? Generate another and revoke the old one on the same screen.

Step 2 — Claude Code

One command. Run it in the project where you want the tools available:

claude code
claude mcp add --transport http topclozer https://topclozer.com/api/mcp \
  --header "Authorization: Bearer tcz_live_YOUR_KEY"

--transport http matters: the default is stdio, which expects a local process to launch, and this is a remote endpoint. Check it landed with claude mcp list.

Step 3 — Claude Desktop

Two routes, depending on your build. The simplest is the connector dialog: Settings → Connectors → Add custom connector, and paste the endpoint. That dialog has nowhere to put a header, which is exactly why the server also accepts the key in the URL:

connector url
https://topclozer.com/api/mcp?key=tcz_live_YOUR_KEY

If your build has no remote-server support, bridge it from the config file (claude_desktop_config.json, reachable via Settings → Developer → Edit Config). This uses mcp-remote, a community bridge that turns a remote HTTP server into a stdio one — it is not ours, and its flags change between versions:

claude_desktop_config.json
{
  "mcpServers": {
    "topclozer": {
      "command": "npx",
      "args": [
        "-y", "mcp-remote",
        "https://topclozer.com/api/mcp",
        "--header", "Authorization: Bearer tcz_live_YOUR_KEY"
      ]
    }
  }
}

Restart Claude Desktop after editing the file — it reads the config only at startup.

A key in a URL is a key in a log

The ?key= form exists because some clients accept nothing else. Where you can send a header, send a header, and use a separate key for the connector so you can revoke it on its own.

Step 4 — verify the connection

In Claude, ask: "which TopClozer tools do you have?"12 should come back, 4 of them LinkedIn tools. To check the endpoint independently of the client, call tools/list yourself:

verify
curl -s https://topclozer.com/api/mcp \
  -H "Authorization: Bearer tcz_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "tools": [
      { "name": "list_campaigns", "description": "List all campaigns with performance stats",
        "inputSchema": { "type": "object", "properties": {} } },
      { "name": "get_stats", "…": "…" },
      { "name": "list_leads", "…": "…" },
      { "name": "get_inbox", "…": "…" },
      { "name": "list_tasks", "…": "…" },
      { "name": "pause_campaign",
        "inputSchema": { "type": "object", "properties": { "id": { "type": "string" } },
                         "required": ["id"] } }
    ]
  }
}

If the key is missing, wrong or revoked you get HTTP 401 and this body instead:

401
{
  "jsonrpc": "2.0",
  "id": 1,
  "error": {
    "code": -32001,
    "message": "Unauthorized: send a workspace API key as 'Authorization: Bearer <key>'"
  }
}

Prompts that work

What the tools add up to in a conversation, and which tool each prompt hits. The first three are research — they need a connected LinkedIn account. The last two read the workspace and work on day one.

"Find 20 VP Engineering people at fintech companies in Berlin, then tell me which three are worth approaching first and why."

search_linkedin_people → get_linkedin_profile

The prospecting loop. Claude runs the search through your sender account, pulls the profiles of the interesting ones, and reasons over the work history and follower counts. The ranking is Claude's judgement, not a score we invented — ask it to show its reasoning and you can argue with it.

"Research this person before my call tomorrow: linkedin.com/in/… — what have they been posting about?"

get_linkedin_profile + get_linkedin_posts

The briefing. One call returns the role, how long they have been in it, follower count and their latest post; the second returns the post history. The strongest opening line usually comes out of the posts rather than the headline.

"Who in my list changed jobs in the last three months?"

search_linkedin_people or list_leads → get_linkedin_profile

jobChangeAt is the epoch-ms start of the current role, so Claude can filter on it directly. A recent move is the strongest timing signal LinkedIn gives away — someone ninety days into a new job is buying, and someone five years in usually is not.

"Which campaign has the worst reply rate — and pause it if it is under 5%."

list_campaigns → pause_campaign

The one end-to-end read-then-write loop. Claude reads replyRate off every campaign, names the worst, and pauses it by id. Ask it to confirm before pausing if you want a checkpoint.

"Summarise the replies that came in since yesterday and flag the ones asking for a meeting."

get_inbox

Conversations come back with their messages and, where classified, an intent field — meeting, interested, question, objection, not_now, not_interested, neutral. Claude does the reading; you get the shortlist.

Each tool's own page lists what it takes and returns: search_linkedin_people, get_linkedin_profile, get_linkedin_posts, list_linkedin_connections.

These prompts improve sharply once Claude also knows who you sell to and what LinkedIn actually permits. Our sibling site publishes that half as free markdown you attach to a Project — context files such as ICP.md and LINKEDIN-LIMITS.md — plus a library of LinkedIn prompts written against the real send ceilings. The tools here are the hands; those files are what stops Claude planning a week of outreach the platform will not allow.

What Claude can and cannot do

Every tool is read-only except pause_campaign. Claude can search LinkedIn, read profiles and read posts — it cannot send an invite, a message, a reply, a follow or a like through MCP; it cannot create or edit a campaign, import leads, or approve a queued draft. The LinkedIn tools are also rate limited to 30 calls per 5 minutes per workspace, so a Claude session that decides to research four hundred people will be told to slow down rather than doing it. Outbound actions are drafted and released by the product under the workspace review mode — by default every invite and message waits for a person — because sending is the one irreversible action in the product.

A key is scoped to one workspace and carries no admin rights. Revoke it in Settings and the next call fails — there is no cached session to wait out. More on the trust model on the security page.

Troubleshooting

401 with -32001 Unauthorized

The key is missing, mistyped, revoked, or your client is not sending the header it promised. Test the same key with the curl above: if curl works and the client does not, the client is dropping the header — use the ?key= URL form instead.

The client connects, then every tool call fails

Expected when there is no key: initialize is answered without authentication so the handshake completes, and the 401 arrives on the first real call. Add the credential to the server entry rather than re-adding the server.

-32601 Method not found

The client asked for something outside initialize, notifications/*, ping, tools/list and tools/call — usually resources/list or prompts/list. Harmless if the client tolerates it; a client that requires resources or prompts cannot use this server.

The client hangs waiting for a stream

This server offers no SSE: a GET with Accept: text/event-stream returns 405. Use the HTTP transport (--transport http), not an SSE transport.

Tools return empty arrays

The workspace really is empty, or the key belongs to a different workspace than the one you are looking at. Call get_stats — it returns zeros for an empty workspace and non-zero counters for a populated one.

HTML comes back instead of JSON

The URL is wrong. The endpoint is exactly /api/mcp; anything else is a marketing page and returns HTML with a 200.

FAQ

Can Claude integrate with LinkedIn?

Not directly — LinkedIn publishes no MCP server and no consumer API for outreach. Claude integrates with a product that operates LinkedIn on your behalf. That is what this server is: TopClozer runs the accounts, sequences and inbox, and exposes them to Claude as MCP tools. Claude reads campaigns, leads and replies, and can pause a campaign; it does not log into LinkedIn.

What is a Claude LinkedIn connector?

"Connector" is Claude Desktop's name for a remote MCP server you add yourself. This endpoint is one: paste the URL into Settings → Connectors → Add custom connector, with the key in the ?key= form because that dialog has no header field. In Claude Code the same server is added with claude mcp add --transport http.

Does it work in Claude Code and Claude Desktop?

Both, by different routes. Claude Code speaks HTTP MCP natively and takes an Authorization header on the command line. Claude Desktop connects either through a custom connector URL or, in builds without native remote support, through the community mcp-remote bridge in claude_desktop_config.json. Any other MCP client that speaks HTTP JSON-RPC works too.

¿Cómo conectar Claude a LinkedIn?

Necesitas una cuenta de LinkedIn conectada al espacio de trabajo (no tu perfil personal), una clave API del espacio de trabajo y un comando: claude mcp add --transport http con la cabecera Authorization: Bearer. La documentación completa está en esta página, en inglés.

Why did my install fail at the first call?

Almost always the key. The endpoint answers an unauthenticated GET — that is discovery, not proof your key works — while every tools/list and tools/call needs one. If your client cannot set headers, the ?key= URL form carries it instead. See the troubleshooting section for the full list.

Is my data sent to Anthropic?

Whatever Claude reads through a tool becomes part of that conversation, which is processed by the model provider under their terms — this is true of every MCP server, ours included. Lead names, message bodies and reply text are exactly what get_inbox and list_leads return, so treat a connected agent as having read access to that data and scope the key accordingly.

Next: every tool, with request and response · the account your agent acts as