Docs / MCP

Model Context Protocol (MCP)

MCP is an open protocol that standardizes how AI applications connect to tools, data, and external systems. This page is the complete reference for MCP's architecture, messages, and code samples.

JSON-RPC 2.0 Open Standard Client–Server
Run live in the Sandbox

Introducing MCP

MCP can be thought of as a USB-C port for AI: just as USB-C provides one physical interface for connecting different devices, MCP provides one software interface for connecting language models to different data sources and tools. Before MCP, every integration between an AI assistant and an external system was written as a bespoke, non-reusable one-off. MCP breaks that pattern: any server written to the MCP spec can be used by any host application that supports MCP.

Why it matters: if your business builds one MCP server, you no longer need to write a separate integration for every new AI assistant (Claude, a smart IDE, a custom agent).

Architecture: Host, Client, and Server

MCP's architecture consists of three distinct roles:

  • Host — the application the user directly works with (like an AI assistant or an IDE). The Host manages permissions and coordinates across multiple connections.
  • Client — lives inside the Host and maintains a 1-to-1, stateful connection with exactly one Server.
  • Server — the application you build; it exposes your data and capabilities to the Host through Resources, Tools, and Prompts.

A Host can connect to several different Servers at once (say, one for inventory, one for CRM), and each of these connections is fully independent and isolated.

The Three Core Primitives of an MCP Server

Resources

Data the Server exposes to the Host — like a document, a database record, or a config file. Each Resource is identified by a unique URI and is usually application-controlled, meaning the host application decides when to read it (similar to a GET request).

Tools

Functions the language model can decide on its own to execute (model-controlled) — like check_inventory() or book_appointment(). Each Tool has a name, a description, and a JSON Schema for input and output. The model decides when to use a Tool based on that description, so writing a precise description matters a great deal.

Prompts

Ready-made, reusable templates that are usually user-controlled — the user consciously selects them (for example, as a quick command in a UI). Prompts help standardize how to interact optimally with your Server.

Sampling and Roots (Advanced)

Beyond the three core primitives, MCP has two advanced capabilities: Sampling lets a Server, in the reverse direction, ask the Host's language model to generate text; and Roots defines the filesystem boundaries the Server is allowed to access.

Transport Layers

TransportUse caseDescription
stdioLocal serversCommunication via the process's standard input/output; the simplest option, suited to when the Server runs on the same machine as the user.
HTTP-based (Streamable HTTP)Remote serversCommunication over HTTP, suited to Servers running as an independent, remote service that require authentication.

Connection Lifecycle

All MCP messages follow the JSON-RPC 2.0 format (three message types: request, response, and notification). A typical connection goes through this cycle:

  1. initialize — the Client announces its protocol version and capabilities to the Server
  2. The Server responds with its own protocol version and capabilities
  3. The Client sends an initialized notification to finalize the connection
  4. Normal operation begins: tools/list, tools/call, resources/list, resources/read, prompts/list, prompts/get
  5. Finally, the connection is closed cleanly

Quick Start: Building a Simple Server

The example below uses the official Python package to build an MCP server with one simple Tool:

from mcp.server.fastmcp import FastMCP

mcp = FastMCP("Store Inventory")

@mcp.tool()
def check_inventory(sku: str) -> dict:
    """Check a product's stock by SKU"""
    # Connect to your real database here
    return {"sku": sku, "in_stock": True, "quantity": 12}

if __name__ == "__main__":
    mcp.run()

These few lines are enough for any MCP-compatible Host to discover this tool and call it at the right moment — with no extra integration code required.

Authentication & Security

For the stdio transport, the security boundary is the same as the OS process boundary. But for remote Servers over HTTP, the following practices are essential:

  • Use a standard authentication mechanism (like OAuth 2.1) to verify the Client's identity
  • Define each Tool with the minimum access it needs; never build one "do-everything" Tool with full database access
  • Log every Tool call so unusual behavior can be traced
  • Apply rate limiting on public Servers

Official SDKs

Official SDKs are available for the main languages, including the mcp package for Python and @modelcontextprotocol/sdk for TypeScript/JavaScript. Unofficial, community-driven SDKs for other languages are gradually being developed too. It's recommended to always start with the latest official SDK.

Best Practices

  • Keep tools small and single-purpose — one Tool, one clear job
  • Write precise descriptions — the model decides whether to use a Tool based on its description, not its name
  • Return structured output — JSON with a fixed shape, not unpredictable free text
  • Report errors clearly — an error message the model can understand, not just a status code
  • Version carefully — make structural changes to Tools cautiously and document them

FAQ

Does MCP replace REST APIs?

Not exactly. MCP is a standard layer on top of your existing logic; behind a Tool, you're usually still calling the same API or database you already have.

Does MCP only work with Anthropic models?

No. MCP is an open standard, meant to work with any model or host application that supports its implementation.

What's the difference between MCP and UCP in OpenCommerce?

MCP is for secure, controlled access to your internal data; UCP is designed for general commercial transactions (search, cart, payment) that any agent can use.