Manage your AI setters programmatically.
SetterFlow ships a remote Model Context Protocol server so you — or an AI agent — can list, create, and edit your own AI setters from Claude Code, Cursor, or any MCP client. Every request is scoped strictly to the account that minted the key.
POST https://www.setterflow.com/api/mcpStreamable HTTPStatelessMint a key, then call the endpoint
Three steps from zero to a live tool call. Most people skip curl and point Claude Code or Cursor at the same URL.
- 1Mint a key
In the dashboard, open Settings → API Keys and create a key with a read or read + write scope. The full
sf_…token is shown once — copy it immediately. - 2Send Bearer auth
Send it on every request as a Bearer token:
Authorization: Bearer sf_… - 3Call JSON-RPC
Speak JSON-RPC over Streamable HTTP: initialize, list tools, then call one. The transport is stateless — each request is authenticated on its own.
# 1) Initialize the session (handshake)
curl -sS https://www.setterflow.com/api/mcp \
-H "Authorization: Bearer sf_your_key_here" \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":1,"method":"initialize",
"params":{"protocolVersion":"2025-06-18",
"capabilities":{},
"clientInfo":{"name":"curl","version":"1.0"}}}'
# 2) List the tools your key can call
curl -sS https://www.setterflow.com/api/mcp \
-H "Authorization: Bearer sf_your_key_here" \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":2,"method":"tools/list","params":{}}'
# 3) Call a tool (list your own chatbots)
curl -sS https://www.setterflow.com/api/mcp \
-H "Authorization: Bearer sf_your_key_here" \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":3,"method":"tools/call",
"params":{"name":"list_chatbots","arguments":{}}}'Client config snippets live in docs/mcp.md.
Two coarse scopes. Nothing in between.
A write key does not implicitly grant read — grant both if a single key should do everything.
20 tools
Read-only tools — list and inspect your data. Safe to hand to something that should only look, never change.
17 tools
Every mutating tool (create / update / delete / configure). A write key can change everything you own — treat it like a password.
37 tools, grouped by area
Generated directly from the live server registry — it always matches what your key can call.
Account
3 toolsWho you are and your account posture.
whoamireadReturn the authenticated caller identity (userId + granted scopes). No database access.
No arguments
get_accountreadGet the caller's own account (identity + subscription posture).
No arguments
update_profilewriteUpdate the caller's own profile (full_name only).
| Arg | Type | Required |
|---|---|---|
full_name | string | required |
Chatbots
5 toolsCreate, read, update, and delete your AI setters.
list_chatbotsreadList the caller's own chatbots (AI setters).
No arguments
get_chatbotreadGet one chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
create_chatbotwriteCreate a chatbot (AI setter) owned by the caller. owner_id is forced server-side.
| Arg | Type | Required |
|---|---|---|
name | string | required |
website_url | string | required |
business_context | string | required |
system_prompt | string | required |
model | string | optional |
status | enum(active | inactive) | optional |
update_chatbotwriteUpdate a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
name | string | optional |
website_url | string | optional |
business_context | string | optional |
system_prompt | string | optional |
model | string | optional |
status | enum(active | inactive) | optional |
delete_chatbotwriteDelete a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
Setter config (lead capture)
2 toolsLead-capture settings — industry template, qualification questions, and collected fields.
get_lead_settingsreadRead lead-capture settings for a chatbot the caller owns (null if unconfigured).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
configure_lead_settingswriteConfigure lead-capture for a chatbot the caller owns. Expands the named industry template server-side; overrides are optional.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
industry | enum(aesthetics | dental | real_estate | home_services | coaching | custom) | required |
enabled | boolean | optional |
qualification_questions | array | optional |
collect_fields | array | optional |
notification_email | string | optional |
notification_webhook_url | string | optional |
Knowledge base
4 toolsPlain-text documents that your setter can answer from.
add_knowledge_documentwriteAdd a plain-text knowledge document to a chatbot the caller owns. Live in the bot's knowledge base on the next chat turn; counts against the document quota.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
title | string | required |
content | string | required |
list_documentsreadList knowledge-base documents for a chatbot the caller owns (crawler-projected docs excluded; document text not included).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
get_documentreadGet one knowledge-base document (including its text content) on a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
documentId | string | required |
delete_documentwriteDelete a knowledge-base document on a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
documentId | string | required |
Website & crawl
4 toolsRegister website sources and trigger background crawls that feed the knowledge base.
add_website_sourcewriteAdd a website source to a chatbot the caller owns (idempotent on URL). The URL must be an http/https address. This only registers the source; call trigger_crawl to start crawling (which runs in the background — poll get_crawl_status).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
url | string (http/https URL) | required |
trigger_crawlwriteTrigger a crawl for a chatbot the caller owns. Provide a sourceId to crawl one source (it must belong to the chatbot, else 'not found'), or omit it to crawl all of the chatbot's sources. Crawling runs in the background — poll get_crawl_status for progress.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
sourceId | string | optional |
list_website_sourcesreadList the website sources for a chatbot the caller owns (each with its seed URL, refresh cadence, and current crawl status).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
get_crawl_statusreadPoll the crawl status for a chatbot the caller owns — one status row per source (last crawl status/time, latest job status, page counts). Use this to track a crawl started by trigger_crawl.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
Follow-ups
4 toolsAutomated follow-up message templates.
list_followupsreadList follow-up message templates for a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
create_followupwriteCreate a follow-up template on a chatbot the caller owns. Requires the followUpSequences feature. delay_minutes is 5..1380 (defaults to 120).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
trigger | enum(no_reply_2h | hot_lead_stall | appointment_reminder) | required |
message_template | string | required |
delay_minutes | number | optional |
is_active | boolean | optional |
update_followupwriteUpdate a follow-up template on a chatbot the caller owns. Send only the fields you want to change.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
followupId | string | required |
trigger | enum(no_reply_2h | hot_lead_stall | appointment_reminder) | optional |
message_template | string | optional |
delay_minutes | number | optional |
is_active | boolean | optional |
delete_followupwriteDelete a follow-up template on a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
followupId | string | required |
Integrations
7 toolsCRM, calendar, and social connections (read + disconnect — connecting a channel is OAuth-only).
list_crm_connectionsreadList CRM connections for a chatbot the caller owns. Secret api_key is never returned.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
create_crm_connectionwriteCreate a CRM connection on a chatbot the caller owns. Requires the crmIntegration feature.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
crm_type | enum(gohighlevel | hubspot | slack | webhook | kommo) | required |
api_key | string | required |
auto_push_enabled | boolean | optional |
push_on_status | enum(hot | warm | any) | optional |
delete_crm_connectionwriteDelete a CRM connection on a chatbot the caller owns.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
connectionId | string | required |
list_calendar_connectionsreadList calendar connections for a chatbot the caller owns. Access/refresh tokens are never returned.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
delete_calendar_connectionwriteDelete calendar connections for a chatbot the caller owns (calendar create is OAuth-only, not available via MCP).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
list_social_connectionsreadList social (Facebook Messenger / Instagram) connections for a chatbot the caller owns. The Meta page access_token is never returned.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
disconnect_social_connectionwriteDisconnect (delete) a social connection on a chatbot the caller owns. Connecting a channel is Meta OAuth and not available via MCP.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
connectionId | string | required |
Analytics
1 toolAccount-level and per-bot usage counters and daily stats.
get_analyticsreadRead analytics. Omit chatbotId for account-level usage (messages, documents, chatbots, social connections for the current period). Provide a chatbotId you own for that bot's message count, last message time, and recent daily stats.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | optional |
Conversations
2 toolsRead widget conversations and their messages.
list_conversationsreadList widget conversations for a chatbot the caller owns (newest first). Returns id, session_id, attribution (the owner's own marketing metadata), and created_at. Social (Messenger/Instagram) conversations are not exposed via MCP yet — widget only.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
limit | number | optional |
offset | number | optional |
get_conversationreadGet one widget conversation and its messages (capped at 100, oldest first) — resolved only after verifying the caller owns the chatbot the conversation belongs to. A conversation you do not own returns forbidden/not found. Widget conversations only.
| Arg | Type | Required |
|---|---|---|
conversationId | string | required |
Leads
2 toolsRead the leads your setters have captured.
list_leadsreadList leads across the caller's own chatbots (or scoped to one chatbot). Cross-tenant leads never appear.
| Arg | Type | Required |
|---|---|---|
chatbot_id | string | optional |
status | enum(hot | warm | cold | converted | lost) | optional |
limit | number | optional |
offset | number | optional |
get_leadreadGet one lead by id, only if the caller owns the chatbot the lead belongs to.
| Arg | Type | Required |
|---|---|---|
leadId | string | required |
Widget
1 toolThe ready-to-paste embed snippet for a bot.
get_widget_snippetreadGet the ready-to-paste HTML embed snippet for a chatbot's widget (a bot the caller owns). Paste it before </body> on the target site.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
Other
2 toolsget_bot_configreadRead a chatbot's widget config (customization JSONB + logo_url) for a bot the caller owns. Null sub-objects mean unset (not default-filled).
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
update_bot_configwriteUpdate a chatbot's widget config (read-merge-write). Send only the top-level customization keys you want to change; omitted top-level keys are preserved. WARNING: a sub-object you include (proactive / articlesTab) REPLACES the stored one wholesale, so send the FULL sub-object with all its fields. logo_url is a separate column (http/https URL, or null to clear) — not part of customization.
| Arg | Type | Required |
|---|---|---|
chatbotId | string | required |
customization | object — see docs/mcp.md | optional |
logo_url | string (http/https URL) | optional |
A few capabilities are deliberately partial
Known edges, called out so you don't discover them mid-build.
OAuth connect is not available
Establishing a new Google Calendar or Facebook/Instagram connection needs an interactive browser consent screen (human OAuth), so there is no connect tool. You can read and disconnect existing connections, but the initial connect happens once in the dashboard.
Logo is a URL, not a file
update_bot_configacceptslogo_urlas an http/https URL string only — there is no binary/image upload over MCP.Conversations are widget-only
list_conversationsandget_conversationreturn widget conversations only; social (Messenger / Instagram) transcripts are not exposed via MCP yet.
Ready to mint a key?
Operators: full deploy and security reference in docs/mcp.md. Everyone else — open the dashboard and create an API key.