Skip to main content
Intercom Fin pulls a user’s recent in-app activity on demand via the Autoplay MCP server — Fin calls it the moment it needs context to answer. One MCP connection, one tool (Get Live User Activity), and a verified identity so Fin asks for the right user.

🎬 Watch the walkthrough

Prefer to watch first? This short Loom walks through the entire setup end to end — adding the MCP server, the tool, identity, and testing the full loop.
Prerequisite: Intercom’s MCP connectors require a US-hosted Intercom workspace.

🔌 Add the Autoplay MCP server

In Intercom: Settings → IntegrationsData connectors. Click the Custom MCP tile (or NewCustom MCP) and enter:
  • Name: Autoplay live activity
  • URL: https://event-connector-luda.onrender.com/mcp
Click Create / Add MCP Server. The server appears in your connectors list showing “(0)” — connected, but no tools added yet.

🧰 Add the Get Live User Activity tool

Click + New under the Autoplay live activity server. In the Add Autoplay live activity connectors modal, check Get Live User Activity and click Add connectors. The tool is added and the count updates to “(1)”.

📝 Open the tool and edit it

Click the Get Live User Activity tool in the list to open it (it opens in Draft). Click Edit to configure it. The tool opens with tabs across the top — API (the endpoint, its inputs, and authentication) and Fin (the prompt that tells Fin when to use the tool). Set up the API tab first (inputs, then authentication), then the Fin tab (the prompt).

🎛️ Configure the data inputs (on the API tab)

On the API tab, the tool has three inputs — product_id, user_id, limit. Set each:
  • product_id → set Data source to Custom value and enter your product id (the same one from your Autoplay SDK setup). Also set the Fallback value to that same product id — so the connector always receives it even if the custom value is ever missing.
  • user_id → choose Use an attribute and select the User ID people attribute. This is the verified id from the Messenger JWT (set up under Verify identity with a Messenger JWT below) — it must equal the stable user id your activity source identifies the user with (e.g. the posthog.identify(...) id, or the Amplitude user_id).
  • limit → optional; leave as Let Fin decide (or ignore it).
For user_id, pick the User ID attribute — not Contact ID and not email. Contact ID is Intercom’s internal integer id; email isn’t the stable key. Activity is stored under your activity source’s stable user id (e.g. the posthog.identify id), so anything else reads an empty bucket.

🔑 Add the authentication token (on the API tab)

Still on the API tab, find the Authentication section. The tool needs your Unkey token, so click New token (Authentication tokensCustom) and fill in:
  • Type: Text
  • Token value: YOUR_UNKEY_TOKEN
  • Token prefix: Bearer
  • Key for request header: Authorization
Save, then back in the connector’s Authentication dropdown, select the token you just created.
The Token prefix field is why you do not type Bearer into the token value — Intercom prepends the prefix for you. The final header sent is Authorization: Bearer YOUR_UNKEY_TOKEN. The token’s external_id must equal your product_id, or calls return 403.

💬 Set the Fin prompt (on the Fin tab)

Now switch to the Fin tab (next to API at the top of the tool). This is where you tell Fin when to use the tool — the field that actually drives Fin’s decision to call it. (The API tab also has a technical description, but the Fin tab’s prompt is the one that matters here.) Replace the default with a clear, Fin-facing trigger description. Recommended:
Use this when a customer references their recent in-app behavior or when understanding their recent actions would help resolve their issue. Specific triggers include:

- Customer asks "what was I just doing?" or "where was I?" or refers to a recent action they took
- Customer mentions encountering an error, bug, or unexpected behavior and you need to see what steps led to it
- Customer is stuck in a flow and needs help figuring out where they are or what to do next
- Customer says "I just clicked something" or "I submitted a form" but is unsure what happened
- You need context about the customer's recent navigation path to troubleshoot or guide them

No input is required from the customer — call this action directly.

This returns a chronological list of the customer's recent in-app activity (oldest to newest), including pages they viewed, buttons they clicked, and forms they submitted.

Do NOT use this when:
- The customer is asking about account details, billing, or subscription information
- The customer is asking about product features or general how-to questions that don't require knowing their recent activity
- The question can be answered without needing to know what the customer recently did in the app
The Fin prompt is the single biggest factor in whether Fin reliably calls the tool. Make it about when to use it, not how it works internally.

🔐 Verify identity with a Messenger JWT

What this is, in plain terms: Fin should only fetch the logged-in user’s activity, so Intercom needs proof of who that user is. A Messenger JWT is a short, signed token your app creates that tells Intercom “this visitor is user X.” You sign it on your server (using a secret from Intercom), then hand it to the Intercom Messenger in your frontend — the same place you already boot Intercom today. The user_id you put in that token must equal the id activity is stored under — the stable user id your activity source identifies the user with (e.g. the one you pass to posthog.identify(...), or the Amplitude user_id). That match is the whole point (see Identity).
How the pieces fit: your frontend asks your server for a token → your server signs it with the Intercom secret → your frontend hands it to Intercom on boot → Intercom trusts the user_id and passes it to Fin.
For logged-in users, Intercom will not give Fin a trusted identity until Messenger JWT verification is set up and enforced (step 4). Until then, lookups come back empty.

1. Get your Unified Secret — in Intercom

Settings → Channels → Messenger → Security. Copy the secret used for identity verification.
This secret is server-side only. Never ship it to the browser, never put it in your frontend bundle, and never commit it — anyone with it can forge any user’s identity. Store it as an env var (e.g. INTERCOM_IDENTITY_SECRET).

2. Sign the token — on your backend

This runs in your server code (where the secret is safe). Add an endpoint your frontend can call to get a token for the currently logged-in user. Node/Express is shown, but any backend works — only the claims (user_id, email, exp) and the HS256 signature matter:
// BACKEND — runs on your server, where INTERCOM_IDENTITY_SECRET is safe.
import jwt from "jsonwebtoken";

// e.g. an Express route your frontend calls after login:
app.get("/intercom-jwt", requireAuth, (req, res) => {
  const token = jwt.sign(
    {
      user_id: req.user.id,   // MUST equal the id you pass to posthog.identify(...)
      email: req.user.email,
      exp: Math.floor(Date.now() / 1000) + 60 * 60, // expires in 1 hour
    },
    process.env.INTERCOM_IDENTITY_SECRET, // the Unified Secret from step 1
    { algorithm: "HS256" }
  );
  res.json({ token });
});

3. Boot the Messenger with the token — in your frontend

Wherever you already initialize the Intercom Messenger (your app’s frontend, after the user logs in), fetch the token from the endpoint above and pass it as the sole identity source:
// FRONTEND — the same place you already boot the Intercom Messenger.
const { token } = await fetch("/intercom-jwt").then((r) => r.json());

window.Intercom("boot", {
  app_id: "YOUR_INTERCOM_APP_ID",
  intercom_user_jwt: token, // the SOLE identity source — do NOT also set user_id/email here
});
Test before enforcing: paste a freshly signed token into a JWT decoder (e.g. jwt.io) and confirm the user_id claim is exactly your activity source’s stable user id (e.g. the value you pass to posthog.identify(...)). A mismatch here is the #1 cause of “Fin sees no activity.”

4. Enforce Messenger Security — in Intercom

Back in Settings → Channels → Messenger → Security, turn on enforcement for the web Messenger. Enforcement is what makes Intercom trust and forward the verified identity to Fin — do this only after step 3 works and your tokens decode correctly.
Use a stable user id for the user_id claim — your internal user primary key, the same one your activity source identifies the user with. Do not use email: emails change, and activity is keyed by the stable id, so an email claim reads the wrong (or empty) bucket.

🧪 Test the connection

On the tool’s Test tab, set test values: product_id (your product) and user_id (a real user you’ve identified and browsed as). Run the live test — you want a 200 with a populated actions array.
  • 401 → the auth token isn’t selected/configured — revisit Add the authentication token above.
  • 200 with empty actions → identity is fine but that user has no recent activity yet (browse as them first).

🚀 Set live

Click Set live. The tool flips from Draft to Live and Fin will call it in real conversations.
On the Fin tab, ensure “Enable Fin to use this connector directly” is checked so Fin triggers it automatically based on the description.

✅ Test the full loop

  1. Log in to your app as a test user (fires your activity source’s identify — e.g. posthog.identify(...) — with that user’s stable id).
  2. Click around — visit a couple of pages, click a button, submit a form.
  3. Open the Messenger as that same logged-in user (the JWT boots with the matching user_id).
  4. Ask Fin: “What have I been doing in the app recently?”
  5. Fin calls Get Live User Activity and answers with what you actually just did.
“No recent activity” = identity mismatch. Confirm the same value in all three:
  1. the id your activity source identifies the user with (e.g. posthog.identify),
  2. the user_id claim in the Messenger JWT,
  3. the User ID attribute you bound on the API tab.
If they don’t match, activity is stored under one key and fetched with another, and the lookup comes back empty.
Once it’s answering correctly, jump into our Discord and say hi — we’ll confirm Fin is pulling activity cleanly and help you tune the trigger description.