MCP Integration
Connect UserTold.ai to Claude, Cursor, or any MCP-compatible agent for direct tool calls, resource reads, and prompts.
Connect
Add to your MCP client config:
Claude Desktop (~/Library/Application Support/Claude/claude_desktop_config.json):
{
"mcpServers": {
"usertold": { "type": "http", "url": "https://mcp.usertold.ai/mcp" }
}
}
Claude Code (.mcp.json in project root or ~/.claude/mcp.json):
{
"mcpServers": {
"usertold": { "type": "http", "url": "https://mcp.usertold.ai/mcp" }
}
}
After adding the config, the client opens a browser login (OAuth 2.1 + PKCE). No manual token handling.
Remote MCP clients can discover OAuth metadata at /.well-known/openid-configuration and /.well-known/oauth-protected-resource. Dynamic client registration is supported at POST /api/oauth/register; pre-registered integrations can still use static clients.
Once connected, call initialize then tools/list to see active tool schemas. Deferred tool schemas are available through MCP resources.
Discover your workspace handle
Before projects.create, discover the authenticated user's default personal workspace handle in one of two supported ways:
- Read
result.user.personal_org_handlefrom theinitializeresponse. - Call
resources/readforusertold://meand readpersonal_org_handle.
Agents should use that handle when they need an orgHandle before a project exists.
projectRef
Most tools are scoped to a project. Accepted formats:
- Unique project handle — e.g.
checkout - Project ID — e.g.
prj_abc123
Agent Workflows
Use these flows to create a study, inspect evidence, and push verified work from an MCP client. Call tools/list, resources/list, and prompts/list for the exact schemas available to your authenticated user.
First connection
Initialize, then find the user's workspace handle:
{
"jsonrpc": "2.0",
"id": "init-1",
"method": "initialize",
"params": {
"protocolVersion": "2025-11-25",
"capabilities": { "tools": {}, "resources": {}, "prompts": {} }
}
}
Use result.user.personal_org_handle from initialize, or read the same value from usertold://me:
{
"jsonrpc": "2.0",
"id": "me-1",
"method": "resources/read",
"params": { "uri": "usertold://me" }
}
Create the first project loop
Create a project in the personal workspace, then create or validate the study and intake:
{
"jsonrpc": "2.0",
"id": "project-1",
"method": "tools/call",
"params": {
"name": "projects.create",
"arguments": { "orgRef": "acme", "name": "Checkout research" }
}
}
Then use the returned project ID or handle with:
studies.validate_scriptwith the script payloadintake.createto create the intakestudies.createwithprojectRef,title,script, andscreener_idstudies.updatewithstatus: "active"to activate the study and linked intake
The dashboard remains the best place to copy the final widget embed and visually confirm the study/intake state.
Read project state before acting
Start with passive resources when the agent needs context:
{
"jsonrpc": "2.0",
"id": "overview-1",
"method": "resources/read",
"params": { "uri": "project://prj_abc123/overview" }
}
Useful reads:
project://{ref}/overviewfor evidence/work counts and coverage gapsproject://{ref}/interviews/recentfor recent interview stateproject://{ref}/evidence/recentfor recent evidenceproject://{ref}/workfor current review packets/workproject://{ref}/studiesandproject://{ref}/intakefor setup state
Use tools when you need filtering, pagination, or mutation.
Inspect evidence and source context
Browse, then inspect source detail:
{
"jsonrpc": "2.0",
"id": "evidence-1",
"method": "tools/call",
"params": {
"name": "evidence.list",
"arguments": {
"projectRef": "prj_abc123",
"signal_type": "struggling_moment",
"min_confidence": 0.7
}
}
}
Before creating work, read the evidence card and, when needed, the interview transcript/events:
evidence.getproject://{ref}/evidence/{signalId}project://{ref}/interviews/{sessionId}project://{ref}/interviews/{sessionId}/transcriptproject://{ref}/interviews/{sessionId}/events
Do not infer delivery work from an evidence title alone. Verify the quote, page context, surrounding actions, and grouping fit.
Create and verify work
Create review context from evidence:
{
"jsonrpc": "2.0",
"id": "work-1",
"method": "tools/call",
"params": {
"name": "work.create_from_evidence",
"arguments": {
"projectRef": "prj_abc123",
"title": "Clarify failed checkout payment state",
"signalIds": ["sig_1", "sig_2"]
}
}
}
Then inspect the work package before handoff:
work.get_evidencefor linked quotes, context, and interview metadatawork.mergewhen two work items describe the same underlying problemwork.updateto move only verified work toreadywork.pushafter you have checked the source evidence and current product context
work.push sends a native issue to GitHub or Linear. It does not decide that the packet is correct.
Tool catalog
Use tools/list for the current schema. The table below summarizes the main tools and when to use them. If a tool is loaded on demand, read usertold://mcp/deferred-tools, then read the listed usertold://mcp/tools/{name} schema before calling it.
projects
| Tool | What it does |
|---|---|
projects.create | Create a new project within an organization. |
projects.update | Update project metadata. Requires owner or admin role. |
projects.delete | Delete a project. Owner only. |
projects.get_context | Deferred: planning snapshot with evidence counts, work item status, active studies, recent interviews, and coverage gaps. |
projects.get_config | Deferred: get masked project settings, including saved OpenAI keys (BYOK). Shows which keys are configured. |
projects.set_config | Deferred: set a project configuration key. Allowed keys: openai_api_key. Owner or admin role required. |
studies
| Tool | What it does |
|---|---|
studies.create | Create a study from a validated script. |
studies.get | Get study details including script, goals, and status. |
studies.update | Update metadata, script, goals, or status (including activation). |
studies.delete | Delete a study. |
studies.validate_script | Validate a study script and return a structural summary. |
interviews
| Tool | What it does |
|---|---|
interviews.list | List interviews with filters (study, status, processing status) and pagination. |
interviews.upload_video | Deferred: upload base64 audio bytes, with optional playback video bytes, as a custom async interview and queue the normal processing pipeline. Read usertold://mcp/tools/interviews.upload_video for the schema. |
interviews.get_context | Deferred: get interview transcript messages within a time window around a given timestamp. |
interviews.processing_status | Deferred: real-time processing status (transcription, evidence extraction) for an interview. |
evidence
| Tool | What it does |
|---|---|
evidence.list | List evidence with filters. Defaults to the product_under_test target surface; pass target_surface="all" to include every surface. |
evidence.coverage_gaps | Deferred: show evidence-to-work coverage gaps and suggested reviewer actions. |
evidence.get | Get full evidence detail including annotation and dismissal state. |
evidence.search | Deferred: semantic + keyword search across evidence. Ranked matches. |
evidence.annotate | Add or update an annotation on an evidence card. |
evidence.dismiss | Dismiss or restore an evidence card — set dismissed=true with a reason to dismiss; dismissed=false to restore. |
evidence.link | Link an evidence card to a work item, or unlink it by passing taskId=null. Evidence is recalculated on affected work items. |
work
| Tool | What it does |
|---|---|
work.list | List work items with filters. Defaults to product_under_test surface and hides closed work items; pass include_closed=true to include done/wont_fix. Pass enriched=true to include signal_types[] and linked_study_ids[] per work item. |
work.search | Deferred: semantic + keyword search across work items. |
work.get_evidence | Deferred: full evidence package for a work item with linked evidence, quotes, context, and interview metadata. |
work.create_from_evidence | Create an evidence review packet/work item from one or more evidence cards and calculate priority context. The created item still needs project-aware review before delivery handoff. |
work.update | Update work item status and/or fields (kanban moves, edits). |
work.merge | Deferred: merge a source work item into a target when two work items describe the same problem. |
work.delete | Delete a work item. |
work.push | Push a work item to a configured provider (GitHub Issues or Linear) with source quotes attached. Use it after source review; the tool does not determine readiness itself. |
intake
| Tool | What it does |
|---|---|
intake.create | Create a new intake with optional inline questions. |
intake.update | Update intake fields or status (includes activation validation). |
intake.set_questions | Replace all questions on an intake — deletes existing questions and inserts the new list in order. |
intake.delete | Delete an intake. |
Resource catalog
Resources are discoverable through resources/list and resources/templates/list. Stable URIs:
Global
usertold://me— current user profile +personal_org_handleusertold://projects— every project the authenticated user can seeusertold://mcp/deferred-tools— deferred tool names with schema URIs for on-demand loadingusertold://mcp/tools/{name}— full schema for a deferred toolusertold://docs/study-design-guide— study design guide for agents (also available viausertold study guide)
The OpenAPI document is published over REST at GET /api/openapi; fetch it from there instead of through MCP.
Project-scoped ({ref} is a unique project handle or prj_...)
project://{ref}/overview— project-level evidence/work item counts and readinessproject://{ref}/evidence/recent— recent evidenceproject://{ref}/evidence/{signalId}— single evidence card with full contextproject://{ref}/interviews/recent— recent interviewsproject://{ref}/interviews/{sessionId}— interview detail (transcript, events, media URLs)project://{ref}/interviews/{sessionId}/transcript— extracted transcript textproject://{ref}/interviews/{sessionId}/events— interview event timelineproject://{ref}/studies— list studiesproject://{ref}/studies/{studyRef}/script— study scriptproject://{ref}/studies/{studyRef}/interviews— interviews under that studyproject://{ref}/work— list work itemsproject://{ref}/work/{taskId}— work item detail with linked evidenceproject://{ref}/intake— list intakesproject://{ref}/intake/{screenerRef}— intake detailproject://{ref}/intake/{screenerRef}/responses— intake response summary
Prompt catalog
Available via prompts/list and prompts/get:
research.draft_study_script— draft a study script for a given objective and block flowresearch.draft_recruitment_story— draft a recruitment story / intake description for a studyresearch.improve_script_iterations— suggest script improvements based on interview resultsresearch.design_roadmap— propose a research roadmap from the current project stateresearch.interpret_study_snapshot— interpret the current state of a study
Research loop
A typical agent workflow:
- Call
projects.get_contextto understand current evidence counts, work item status, and coverage gaps - Design and activate a study (
studies.validate_script→studies.create→studies.updateto activate) - Interviews run automatically as users interact with the widget
- List, inspect coverage gaps, and curate extracted evidence (
evidence.list/evidence.coverage_gaps/evidence.search/evidence.annotate/evidence.dismiss/evidence.link) - Create evidence review packets from evidence clusters (
work.create_from_evidence) - Review source evidence (
work.get_evidence), merge duplicates (work.merge), and decide which packets are delivery-ready - Use
work.pushfor work items you have verified and decided are delivery-ready - Complete linked Linear issues so current evidence resolves and future interviews can be watched for possible recurrence
Troubleshooting
| Symptom | Next action |
|---|---|
| The client tries SSE or GET | Use stateless JSON-RPC over POST /mcp; GET returns 405. |
| Login does not open or complete | Check OAuth discovery at /.well-known/openid-configuration and /.well-known/oauth-protected-resource; normal Claude/Cursor setup should use OAuth + PKCE, not pasted bearer tokens. |
Unsupported MCP-Protocol-Version | Initialize with 2025-11-25 or 2024-11-05. |
Project not found or unauthorized | Read usertold://me, confirm the user belongs to the project, and pass projectRef as a unique project handle or project ID. |
Entity not found | Confirm the evidence, interview, intake, study, or work item belongs to the same projectRef used in the call. |
Tool name is missing from tools/list | Read usertold://mcp/deferred-tools, then read the listed usertold://mcp/tools/{name} schema before calling it. |
| Agent created work too early | Read work.get_evidence and source interview resources, then update or dismiss the packet before pushing. |
work.push fails | Confirm a tracker is connected, the work was verified, and the provider choice matches project settings. |
See also
- CLI Reference — command-line alternative to MCP tools
- API Reference — raw REST endpoints
- Quickstart — end-to-end setup guide
- Core Concepts — product model behind projects, interviews, evidence, and work
- Methodology — evidence interpretation and verification guidance