chatform

MCP server

Connect Claude, ChatGPT or Cursor to your forms and let them read, analyse and build.

Chatform runs a Model Context Protocol server at:

https://api.chatform.in/mcp

Point an AI assistant at it with an API key and it can list your forms, read responses, analyse completion rates, author a new form from a description, publish it, and reach the rest of the API when it needs something the named tools do not cover.

It is the same worker, the same keys and the same scopes as /v1. Nothing here can do anything your key could not already do over HTTP — with one deliberate subtraction: nothing can delete.

Get a key

MCP needs more than a new key is given by default. A default secret key can read forms and responses; it cannot publish, read analytics or export, so an assistant using one fails with insufficient_scope on the first interesting request.

In Settings → API keys, create a secret key with these scopes:

ScopeWhy
form:read, form:write, form:publishRead, edit and publish forms
response:read, response:writeRead responses, and submit them
response:exportStart exports
analytics:readCompletion rates and per-question funnels
webhook:read, webhook:writeInspect and register webhooks

GET /api/keys/scopes returns this set as the agent preset if you are building your own key UI.

This is a secret key, so it belongs on a machine, not in a page. /mcp refuses publishable (pk_) keys outright — their ceiling excludes reading responses and analytics, so almost nothing would work anyway. Treat the key like a password: an assistant that holds it can read every response you have collected.

Install

claude mcp add --transport http chatform https://api.chatform.in/mcp \
  --header "Authorization: Bearer $CHATFORM_SECRET_KEY"

Connecting from claude.ai or ChatGPT as a consumer connector needs OAuth, which is not built yet — see What is not here.

The tools

Twenty-four, which is a budget rather than an accident: clients cap how many tools they will load — Cursor at forty — and that ceiling is shared with every other server you have connected.

Getting oriented

ToolScope
whoamiWhich org this key is, what it may do, and what it is missing

Forms

ToolScope
list_formsform:readYour forms, newest first
get_formform:readOne form. Defaults to the editable document, which is what to change
list_blocksEvery question type, its config schema and answer contract
create_formform:writeCreate a form, empty or fully authored
update_formform:writeReplace the working document
publish_formform:publishMake the working document live

Responses

ToolScope
list_responsesresponse:readA page of responses; answers are opt-in
search_responsesresponse:readFind responses containing a piece of text
get_responseresponse:readOne response with all its answers
submit_responseresponse:writeRecord a response — for imports, or answering on someone's behalf
get_form_analyticsanalytics:readViews, completion rate, per-question funnel, distributions
export_responsesresponse:exportStart a CSV or JSON export
check_exportresponse:exportPoll an export and get its download link
get_filefile:readResolve a file-upload answer's fileId to a name and a download link

Webhooks

ToolScope
list_webhookswebhook:readRegistered endpoints and their events
list_webhook_deliverieswebhook:readRecent attempts, statuses and errors — for "why is it quiet"
list_eventsEvery event name a webhook can subscribe to
create_webhookwebhook:writeRegister one. The signing secret is shown once
replay_webhook_deliverywebhook:writeRe-send one failed delivery

Everything else

Four tools reach the whole developer API without putting forty more schemas in front of the model:

Tool
chatform_api_searchFind an endpoint by keyword; returns its path and required scope
chatform_api_detailsThat endpoint's parameters and response schema
chatform_api_readGET any documented endpoint
chatform_api_writePOST, PUT or PATCH any documented endpoint

They are bounded by the spec: only the operations published at https://api.chatform.in/openapi.json are reachable. The dashboard's own /api/* routes and the respondent /p/* channel are not part of that document and cannot be called with a key, so an assistant cannot reach them however it asks.

Two areas are reachable only this way, on purpose:

  • Driving a live conversation — opening a chat session and exchanging messages turn by turn, plus session uploads. Fifteen operations, and a niche job for an assistant: submit_response records answers directly without pretending to be a respondent. If you want named tools for testing a form conversationally, that is a reasonable ask.
  • Incremental response building — recording answers one at a time, then completing or abandoning GET /v1/responses/{id}/next and its siblings. submit_response does the one-shot version, which is what an import or an agent filling a form actually needs.

Building a form

There is no "generate a form" tool, and that is on purpose — your assistant is already the model. It reads list_blocks for the question-type contract, writes the document itself, and calls create_form. Chatform spends nothing on inference, and you are not paying twice for the same sentence.

Build me a 5-question customer onboarding form, publish it, and show me the completion rate once people start answering.

That runs list_blockscreate_formpublish_formget_form_analytics.

When editing an existing form, the assistant must read the document first: update_form replaces the whole draft, so a partial document silently removes every question missing from it.

What is not here

  • Deletes. No tool deletes a form, a response, an answer or a webhook, and chatform_api_write refuses the DELETE method outright — whatever scopes the key holds. Respondent free text is attacker-controlled input, and an assistant reading it should not be one confused tool call away from destroying data. Delete from the dashboard.
  • Key and plan management. No key can mint keys or change a plan; see Scopes.
  • OAuth, so claude.ai's and ChatGPT's connector dialogs — which want it rather than a static header — cannot install this yet. Bearer keys work in Claude Code, Cursor, VS Code and Codex today.
  • .xlsx. The API exports csv and json; the typed workbook is dashboard-only. See Spreadsheets.

Plan and usage

/mcp is part of the developer API, so it needs a plan that includes API access, and every tool call that reaches an endpoint counts as one request against your monthly quota. Listing the tools is free, which is why an assistant can connect and show you what it could do before the plan refuses the first call — and the refusal says which plan lifts it.

Per-question analytics needs a plan with advanced analytics. Below that, get_form_analytics returns the headline numbers and says which sections the plan withheld, so an assistant will not report an empty funnel as "no data".

Things to know

  • search_responses is a substring match, not semantic search, and results are not ranked. Searching unhappy will not find dissatisfied. To find themes, page through list_responses with answers included and read them.
  • Results are paginated small — ten rows by default — and long answers are truncated with a truncated flag rather than silently cut.
  • Exports are never inlined. export_responses returns an id; check_export returns a short-lived signed link, re-minted on each read.
  • Keys pinned to specific forms still are. A restricted key sees 404 for anything outside its list, through MCP as over HTTP.

Troubleshooting

What you seeWhat it means
unauthorized on connectNo key, or the header is not reaching the server
secret_key_requiredYou used a pk_ key. /mcp needs sk_
secret_key_in_browserA secret key arrived with an Origin header. /mcp is server-to-server
insufficient_scopeThe key is missing the scope named in the message — mint one with the scopes above
feature_lockedThe plan does not include API access; the message carries the upgrade link
limit_reachedThe monthly request quota is spent; the message says when it resets
not a documented Chatform endpointA passthrough tool was pointed at something outside the developer API

Every error carries a request_id. Quote it if you contact support.

On this page