Protocol Implementation
Model Context Protocol implementation details for MCP.do
MCP.do implements the Model Context Protocol specification, providing a standardized interface for AI models to access platform capabilities.
Protocol Overview
The Model Context Protocol (MCP) is a specification for enabling AI models to:
- Discover capabilities through standardized tool and resource schemas
- Execute operations via JSON-RPC over HTTP or SSE
- Access context through resources and prompts
- Request input via elicitation for human-in-the-loop workflows
Transport Layer
MCP.do supports both HTTP JSON-RPC and Server-Sent Events (SSE) transports:
JSON-RPC Request/Response Flow
HTTP JSON-RPC
Standard JSON-RPC 2.0 over HTTP POST:
POST https://mcp.do/
Content-Type: application/json
Authorization: Bearer sk_live_xxxxx
{
"jsonrpc": "2.0",
"id": 1,
"method": "tools/call",
"params": {
"name": "do",
"arguments": {
"script": "db.Businesses.list()"
}
}
}Server-Sent Events (SSE)
Long-lived connection for streaming responses:
GET https://mcp.do/
Accept: text/event-stream
Authorization: Bearer sk_live_xxxxx
// Server sends events:
event: message
data: {"jsonrpc":"2.0","method":"notifications/initialized"}
event: message
data: {"jsonrpc":"2.0","id":1,"result":{...}}Protocol Methods
Initialization
// Client sends initialize request
{
"jsonrpc": "2.0",
"id": 1,
"method": "initialize",
"params": {
"protocolVersion": "2024-11-05",
"capabilities": {
"roots": { "listChanged": true }
},
"clientInfo": {
"name": "my-client",
"version": "1.0.0"
}
}
}
// Server responds with capabilities
{
"jsonrpc": "2.0",
"id": 1,
"result": {
"protocolVersion": "2024-11-05",
"capabilities": {
"tools": {},
"prompts": {},
"resources": {}
},
"serverInfo": {
"name": "mcp.do",
"version": "1.0.0"
}
}
}List Tools
// Request available tools
{
"jsonrpc": "2.0",
"id": 2,
"method": "tools/list"
}
// Response with tool definitions
{
"jsonrpc": "2.0",
"id": 2,
"result": {
"tools": [
{
"name": "do",
"description": "Execute TypeScript against sdk.do...",
"inputSchema": {
"type": "object",
"properties": {
"script": {
"type": "string",
"description": "TypeScript code to execute"
}
},
"required": ["script"]
}
},
{
"name": "elicit",
"description": "Request structured input from user...",
"inputSchema": {
"type": "object",
"properties": {
"message": { "type": "string" },
"schema": { "type": "object" },
"uiType": { "type": "string", "enum": ["slack", "discord", "teams", "web"] }
},
"required": ["message", "schema"]
}
}
]
}
}Call Tool
// Execute a tool
{
"jsonrpc": "2.0",
"id": 3,
"method": "tools/call",
"params": {
"name": "do",
"arguments": {
"script": "db.Businesses.list()"
}
}
}
// Response with result
{
"jsonrpc": "2.0",
"id": 3,
"result": {
"content": [
{
"type": "text",
"text": "[{\"id\":\"biz_123\",\"name\":\"Acme Corp\"}]"
}
]
}
}Authentication Flow
OAuth 2.1 Discovery
MCP.do provides OAuth 2.0 Protected Resource Metadata (RFC 9728):
GET https://mcp.do/.well-known/oauth-protected-resource
{
"resource": "https://mcp.do",
"authorization_servers": ["https://ooauth.do"],
"scopes_supported": ["mcp:tools", "mcp:resources", "mcp:prompts"],
"bearer_methods_supported": ["header"],
"resource_signing_alg_values_supported": ["RS256"],
"resource_documentation": "https://mcp.do/docs",
"resource_policy_uri": "https://mcp.do/policy"
}WWW-Authenticate Header
When authentication fails:
HTTP/1.1 401 Unauthorized
WWW-Authenticate: Bearer realm="https://mcp.do",
resource="https://mcp.do/.well-known/oauth-protected-resource",
authorization_server="https://ooauth.do"
Content-Type: application/json
{
"error": "invalid_token",
"error_description": "Token validation failed",
"resource": "https://mcp.do/.well-known/oauth-protected-resource"
}Elicitation Protocol
MCP.do implements the elicitation protocol (2025-06-18) for human-in-the-loop workflows:
Request Input
{
"jsonrpc": "2.0",
"id": 4,
"method": "tools/call",
"params": {
"name": "elicit",
"arguments": {
"message": "Do you approve this order?",
"schema": {
"type": "object",
"properties": {
"approved": {
"type": "boolean",
"description": "Approval decision"
},
"reason": {
"type": "string",
"description": "Reason for decision"
}
},
"required": ["approved"]
},
"uiType": "slack"
}
}
}User Accepts
{
"jsonrpc": "2.0",
"id": 4,
"result": {
"content": [
{
"type": "text",
"text": "User provided: {\"approved\":true,\"reason\":\"Order looks good\"}"
}
]
}
}User Declines
{
"jsonrpc": "2.0",
"id": 4,
"result": {
"content": [
{
"type": "text",
"text": "User declined: Not comfortable with this amount"
}
],
"isError": true
}
}Error Handling
Authentication Errors
{
"jsonrpc": "2.0",
"id": 1,
"error": {
"code": -32001,
"message": "Authentication required",
"data": {
"error": "invalid_token",
"error_description": "Token validation failed"
}
}
}Rate Limit Errors
HTTP/1.1 429 Too Many Requests
X-RateLimit-Limit: 10
X-RateLimit-Window: 60
{
"jsonrpc": "2.0",
"id": 1,
"error": {
"code": -32002,
"message": "Rate limit exceeded"
}
}Execution Errors
{
"jsonrpc": "2.0",
"id": 1,
"result": {
"content": [
{
"type": "text",
"text": "Error: Cannot read property 'name' of undefined\n at line 3:15"
}
],
"isError": true
}
}Implementation Details
MCP Agent Base Class
MCP.do uses the McpAgent base class from the internal agents/mcp package (part of the .do platform monorepo):
// Note: 'agents/mcp' is an internal package in the .do platform
// For external implementations, use @modelcontextprotocol/sdk directly
import { McpAgent } from 'agents/mcp'
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js'
class PublicMcpAgent extends McpAgent<Env, unknown, PublicMcpUserProps> {
server = new McpServer({
name: 'mcp.do',
version: '1.0.0',
})
async init() {
// Register tools
this.server.tool('do', '...', schema, handler)
this.server.tool('elicit', '...', schema, handler)
}
}Durable Objects
Two Durable Objects provide isolation and persistence:
ExecutionSandbox:
- Isolated environment per request
- Timeout enforcement
- Resource limits
RateLimiter:
- Sliding window rate limiting
- Persistent storage
- Automatic TTL cleanup
Request Context
Auth context flows through the execution pipeline:
// In fetch handler
const auth = await authenticateRequest(authHeader, env)
// Pass to MCP agent via execution context
const ctxWithProps = {
...ctx,
props: { auth },
}
// Available in tool handlers
const auth = this.props?.authProtocol Extensions
On-Demand Documentation
MCP.do extends the protocol with documentation requests:
// Request documentation
{
"name": "do",
"arguments": {
"script": "db.md" // Special .md suffix
}
}
// Returns markdown documentation
{
"content": [
{
"type": "text",
"text": "# Database Module\n\n..."
}
]
}Admin Tools
Admin users get additional tools via role-based access:
// Only available to users with admin role
{
"name": "admin_deploy_worker",
"description": "Deploy a Cloudflare Worker",
"inputSchema": {
"type": "object",
"properties": {
"name": { "type": "string" },
"script": { "type": "string" }
}
}
}Events Tools
Authenticated users get event management tools:
{
"name": "events_list",
"description": "List recent events",
"inputSchema": {
"type": "object",
"properties": {
"type": { "type": "string" },
"limit": { "type": "number" }
}
}
}Next Steps
- The
doTool - TypeScript execution details - The
elicitTool - Human-in-the-loop workflows - Authentication - Auth implementation
- Integration Guide - Client integration patterns