Skip to content

MCP Server

Bubbles exposes a Model Context Protocol (MCP) server so AI assistants can read your teams, bubbles, transcripts, and comments — and send the notetaker to record a meeting — directly. It is a remote, streamable-HTTP MCP server protected by OAuth 2.1 (the same authorization server described in Authentication).

Connecting takes no setup and no token to paste: your assistant adds the URL, the OAuth handshake runs automatically, and Bubbles opens in your browser so you can sign in — or create an account — the same way you sign in to Bubbles itself. You land back in the conversation with your assistant bound to your real Bubbles account.

Endpoint

https://api-tom.usebubbles.com/mcp

The server advertises its OAuth requirements at https://api-tom.usebubbles.com/.well-known/oauth-protected-resource/mcp. A compliant MCP client discovers the authorization server automatically, registers itself (dynamic client registration), and completes a PKCE authorization — which opens Bubbles in your browser. There you log in to an existing account or create a new one, with Google, Microsoft, or an emailed code, exactly as on the Bubbles web app. If you are new, you finish setting up your workspace and calendar there too. The connection is then bound to your account, and the tools that read your data work.

Connector URLs

Add whichever matches how you want to start. They expose the identical tools and both keep your data locked until a Bubbles account is bound; they differ only in where you sign in.

ConnectorURLWhat happens when you add it
Defaulthttps://api-tom.usebubbles.com/mcpOpens Bubbles in your browser to sign in or sign up — with Google, Microsoft, or an emailed code — and binds this connection to that account. Recommended for most users.
Seamlesshttps://api-tom.usebubbles.com/mcp-seamlessConnects instantly with no browser step — an anonymous session — and you sign in later, in plain language, inside the conversation (below). Use it when you would rather not leave the chat.

Connect

In Settings → Connectors → Add custom connector, give it a name and set the server URL to your Bubbles MCP endpoint:

https://api-tom.usebubbles.com/mcp

Claude opens Bubbles in your browser to sign in or create an account. Once you are done, the Bubbles tools appear in the composer’s tool menu and work on your account right away.

After you sign in

Your assistant picks the thread back up by calling bubbles_whats_next, which tells it whether anything still needs setting up and what it can do for you now. If you already have a workspace it will not ask you to make another — it just gets to work.

Advanced: sign in inside the conversation

If you would rather not leave the chat — or your client cannot open a browser — add the seamless connector instead:

https://api-tom.usebubbles.com/mcp-seamless

It connects as an anonymous session: the tools are listed, but the read tools return a short “the user is not signed in yet” message with no data and join_meeting will not dispatch, so nothing about any account is exposed until you sign in. Signing in then happens entirely in the chat, with no password and no token to copy:

  1. Ask the assistant to sign you in (for example, “Sign me in to Bubbles.”). It calls bubbles_signup_start (or bubbles_login_start — they are the same unified flow) with your email, and Bubbles emails you a sign-in code. The same flow logs in existing users and creates an account for new ones, so you never have to say which you are.
  2. Read the code back to the assistant. It calls bubbles_signup_verify with only the code — the connection already knows which sign-in is in progress, so there is no session token to pass around. This finishes signing you in.
  3. If you are new, the assistant offers to set up a workspace: bubbles_signup_workspaces looks for an existing workspace your email domain can join, and bubbles_signup_workspace creates a new one (or joins/enables domain auto-join). A newly created workspace may include a free Pro trial.

Once you are signed in, the read tools return your data and join_meeting works — on the same connection, in the same conversation.

Tools

Beyond the sign-in tools above, the connector registers seven data tools — six read-only tools (the same read surface as the REST API, sharing one read core so results are consistent) plus one write tool, join_meeting. Each tool’s annotations are truthful: the six read tools are marked read-only, and join_meeting is marked as not read-only and open-world (it reaches an external meeting platform), so a client can gate it accordingly.

Tool Title Type Does
list_bubbles List bubbles read List the caller’s bubbles (paginated; supports the same filters as GET /v1/bubbles).
search_bubbles Search bubbles read Search the caller’s bubbles by keyword (title, author, and meeting notes), ranked by relevance.
get_bubble Get bubble read Fetch a single bubble by id.
get_bubble_transcript Get bubble transcript read Fetch a bubble’s diarized transcript (chunked: default 50k, max 120k chars per call).
get_bubble_comments Get bubble comments read List a bubble’s comments (paginated).
list_teams List teams read List the caller’s teams, plans, roles, and channels.
join_meeting Join & record a meeting write Send the notetaker to join and record a meeting by link (requires the meetings:join scope).

Schemas

  • list_bubbles — inputs: team_id?, type? (meeting_recording | screen_recording | custom_image), created_after?, created_before?, limit (1–100, default 20), cursor?. Returns { bubbles[], has_more, next_cursor? }.
  • search_bubbles — inputs: query (required — matched against a bubble’s title, its author’s name, and its AI-generated meeting notes/summary, so a keyword that appears only inside the notes still finds the bubble; title matches rank highest, then author, then notes), plus the same optional filters as list_bubbles (team_id?, type?, created_after?, created_before?, limit, cursor?). Returns the same { bubbles[], has_more, next_cursor? } shape, ranked by relevance. Use it when the user names a topic, project, person, meeting, or something discussed in a meeting; only bubbles the user can access are ever returned.
  • get_bubble — input: bubble_id. Returns the full bubble object (title, url, author, participants, media, summary, action items, …).
  • get_bubble_transcript — inputs: bubble_id, format (text | json, default text), offset_chars (default 0), max_chars (1,000–120,000, default 50,000). Returns { transcript, offset_chars, returned_chars, total_chars, has_more, next_offset? }.
  • get_bubble_comments — input: bubble_id. Returns { bubble_id, comments[] }.
  • list_teams — no inputs. Returns your teams, plans, roles, and channels.
  • join_meeting (write) — inputs: meeting_url (a Google Meet, Microsoft Teams, Zoom, Webex, or GoTo link — any other link is rejected and no notetaker is sent), team_id (from list_teams — the workspace to record into). Sends the Bubbles notetaker to join and record the meeting and returns the dispatched meeting-join resource { id, type: "meeting_join", status: "dispatched", meeting_url, team_id, created_at }. Requires the meetings:join scope (personal access tokens carry it implicitly; an OAuth connection carries it too).

Large transcripts are chunked

get_bubble_transcript returns at most 50,000 characters by default and never more than 120,000 in a single call. When a transcript is longer, the response sets has_more: true and returns a next_offset; call again with offset_chars: next_offset to fetch the next chunk. Chunk boundaries snap back to the last newline so a speaker turn is never split mid-block. total_chars tells you the full length up front.