MCP in Plain English: AI's USB-C Moment
One protocol between models and tools. What it replaces and why every vendor adopted it.
The Model Context Protocol (MCP) is an open, JSON-RPC-based standard that lets AI applications and large language models discover and invoke external tools, data sources, and prompt workflows through a single, vendor-neutral interface. It splits the world into hosts (AI apps), clients (protocol handlers), and servers (capability providers), replacing ad-hoc plugin systems with a rigorously specified, transport-agnostic protocol.
Every major AI vendor now converges on a single protocol for tool access: Anthropic, OpenAI, Google DeepMind. That protocol was not designed by a standards body. It started as an internal project at Anthropic and is now stewarded by the Linux Foundation. This convergence is the USB-C moment for AI tooling. It means you can write one connector and have it work everywhere.
Why did AI tools need a standard protocol?
Before MCP, connecting an LLM to a real-world tool meant writing custom glue for each platform. You built a function for ChatGPT’s function calling API (application programming interface). You wrote a plugin for Claude’s tool use. You wrapped it again for LangChain or a custom agent. Each integration was a one-off that tied you to a vendor.
This fragmentation created real pain. Engineers had to maintain multiple tool implementations, each with its own schema, error handling, and authentication flow. Switching model providers meant rewriting every tool connector. The lack of a shared interface also made it hard to compose tools from different sources or to reuse them across projects.
MCP solves this by defining a single protocol between an AI host and external capability providers. It is not a framework or an orchestration layer. It is the wire format and the lifecycle rules that let any host talk to any server. The analogy is USB-C: before USB-C, every device had its own port and cable. After USB-C, one cable works for phones, laptops, monitors, and peripherals. MCP does the same for AI tools. One protocol, many hosts, many servers.
This is not just a convenience. It changes the economics of building AI-powered assistants. Instead of betting on a single model vendor, you can build a personal assistant that connects to files, calendar, music, and smart home tools through MCP servers. Swap the underlying LLM without touching the tool layer. That is the promise, and the rest of this article shows how it works under the hood.
- 3 platforms × 3 tools = 9 custom integrations
- Every tool per platform needs separate schema, auth, and error handling
- Locked to one model vendor, hard to switch
- 1 MCP server per tool, any host can use it
- One protocol, one schema, consistent auth
- Model agnostic, swap hosts freely
How does MCP structure communication between models and tools?
MCP separates the world into three roles: host, client, and server. The host is the AI application that runs the model and manages the conversation. The client is a protocol adapter that maintains a stateful JSON-RPC session to exactly one server. The server is a program that exposes a catalog of tools, resources, or prompts.
Imagine you are building a personal assistant. The host is your assistant app. It embeds an LLM and shows a chat interface. To give it access to your local files, you configure a filesystem MCP server. To check your calendar, you add a Google Calendar MCP server. For music control, a Spotify MCP server. For smart home, a Home Assistant MCP server. Each server runs independently, either locally as a child process or remotely over HTTP.
The host does not speak MCP directly to these servers. For each server, the host creates an MCP client object. That client establishes a dedicated JSON-RPC connection and handles all protocol messages. The host asks the client to list tools, call a tool, or read a resource. The client translates those requests into the correct JSON-RPC method calls and returns the results. This keeps the host’s orchestration logic clean and decoupled from transport details.
The lifecycle of any MCP connection follows three phases: initialization, operation, and shutdown. When a client first connects, it sends an initialize request that includes its protocol version and supported capabilities. The server responds with its own version and features. If the versions match, the client sends an initialized notification, and the session enters the operation phase. During operation, the client can call tools/list, resources/list, prompts/list, and invoke specific tools or resources. When the host is done, it sends a shutdown request, the server cleans up, and the connection closes.
This stateful session model is important. It means capabilities are negotiated once and remain stable for the lifetime of the connection. The host knows exactly what each server provides and can present that to the LLM as a set of available functions. When the model decides to call a tool, the host uses the same client to send a tools/call request with the tool name and arguments. The server executes the logic and returns structured content. The host then injects that result back into the model’s context.
Consider a concrete flow from our personal assistant. The user types, “Summarize my notes from today.” The host has already connected to the filesystem MCP server via stdio, discovered the read_file tool, and registered it with the LLM. The LLM emits a tool call for read_file with the path /notes/2026-07-02.md. The host maps this to a tools/call request through the filesystem client. The server reads the file and returns its content. The host feeds that content back into the prompt, and the LLM generates a summary.
This clean separation between host logic and server implementation is what makes MCP composable. You can swap the filesystem server for a cloud storage server without changing the assistant code. You can run the same server with Claude Desktop, ChatGPT, or a custom agent. The protocol boundary is the contract.
What are tools, resources, and prompts in MCP?
MCP defines three first-class primitives that servers can expose. Tools are executable functions. Resources are data that can be read. Prompts are reusable, parameterized templates for interactions. Each primitive has its own discovery method and invocation semantics.
A tool is the mechanism by which an LLM does something in the outside world. It takes structured arguments and returns structured content. Servers advertise their tools via tools/list, returning descriptors that include a name, a description, and a JSON (JavaScript Object Notation) Schema for the input parameters. Hosts convert these descriptors into tool definitions that the LLM can call. When the model invokes a tool, the host sends a tools/call request with the tool name and the arguments the model provided. The server executes the underlying function and returns a result.
In our assistant, the calendar MCP server might expose a tool called create_event with parameters like summary, start_time, and end_time. The music server might expose play_track with a track_id. The assistant’s LLM can call these just like any other function, and the host handles the protocol translation.
A resource is a piece of data that can be read. It is not an action. It is a document, a file, a database record, or the output of a search query. Servers list resources via resources/list and can also expose resource templates with URI patterns. Clients read a specific resource with resources/read, and the server returns content blocks that may include text or binary data. Hosts often use resources to inject context into the LLM prompt before the model generates a response.
The calendar server might expose a resource like today_schedule that returns a list of events. The assistant can read that resource and pass it to the LLM as part of the prompt when the user asks, “What does my day look like?” The LLM never calls a tool for this. It just receives the data as context.
A prompt is a higher-level primitive. It is a named template with argument definitions that a server can provide. Servers list prompts with prompts/list, and clients retrieve an expanded prompt with prompts/get by supplying argument values. Prompts are designed to be user-controlled. The intent is that a user explicitly chooses to run a prompt workflow, rather than the LLM autonomously triggering it.
Our assistant could use a prompt from the smart home server called goodnight_routine. This prompt might include a template that turns off lights, locks doors, and sets the thermostat. The user selects it from a slash command menu, the host fetches the expanded prompt, and the LLM executes the sequence using the appropriate tools. Prompts let domain experts encode best-practice workflows directly into servers.
These three primitives give MCP a clean separation of concerns. Tools handle actions with side effects. Resources handle data retrieval for context. Prompts handle reusable, user-initiated workflows. A single server can expose any combination of them, and hosts can decide which to surface based on their UX needs.
How does MCP handle authentication and remote servers?
MCP supports two transport modes with different security models. For local servers, it uses stdio. The host launches the server as a child process and communicates over standard input and output. Authentication is implicit: the server inherits the user’s filesystem permissions or local credentials. This is simple, fast, and ideal for tools that access the local machine.
For remote servers, MCP defines an OAuth 2.1 authorization framework on top of HTTP transports. The MCP server acts as an OAuth resource server. The MCP client acts as an OAuth client. When a client tries to access a protected server without a valid token, the server responds with an HTTP 401 and a WWW‑Authenticate header that includes a scope parameter. The client then obtains an access token from an authorization server, typically using the authorization code flow, and retries the request with a bearer token. Every subsequent HTTP request must include the token.
This means you can run a GitHub MCP server remotely and connect to it from any MCP-compatible host. You provide a GitHub personal access token during setup, and the MCP client manages the OAuth flow or uses the token directly. The server then calls the GitHub API on your behalf, respecting your permissions. The same pattern works for Stripe, Slack, or any service that exposes an MCP server.
OpenAI’s Agents SDK (software development kit) demonstrates how vendors integrate these transports. It supports three categories of MCP servers: hosted tools where the server runs inside OpenAI’s infrastructure, streamable HTTP servers that you host yourself, and local stdio servers. In all cases, the underlying tool calling semantics remain the same. The host discovers tools via tools/list and invokes them with tools/call. The transport and authentication details are handled by the client layer.
This layered design is what makes MCP a true protocol. The semantics of tools, resources, and prompts are independent of how the bytes move. You can start with a local filesystem server over stdio during development and later deploy the same server behind an OAuth-protected HTTP endpoint without changing a single line of tool-calling code in your assistant.
Quick Reference
| Property | Value |
|---|---|
| Protocol | JSON-RPC 2.0 |
| Transports | stdio, streamable HTTP (SSE deprecated) |
| Primitives | tools, resources, prompts |
| Authorization | OAuth 2.1 for HTTP transports |
| Specification | MCP Specification |
| Reference SDKs | Python, TypeScript, Java, Kotlin |
| Example servers | Filesystem, GitHub, Stripe |
| Host integrations | OpenAI Agents SDK, LangChain |
Frequently Asked Questions
Q: Do I need to use Anthropic’s Claude to use MCP? No. MCP is an open protocol. Any application can implement the host side. ChatGPT, VS Code agents, LangChain, and many others already support MCP. You can build a host from scratch using the public SDKs.
Q: Is MCP only for remote servers, or can I run it locally? Both. The stdio transport lets you run servers locally as child processes. Streamable HTTP supports remote servers. You can mix local and remote servers in the same host session.
Q: How does MCP handle authentication for third-party services? For HTTP transports, MCP defines an OAuth 2.1 framework. The server acts as a resource server, the client obtains access tokens, and every request includes a bearer token. For local stdio, the server typically relies on the user’s existing credentials.
Q: What is the difference between a tool and a resource? A tool is an executable function with side effects, like creating a calendar event. A resource is a piece of data that can be read, like today’s schedule. Resources are often used to inject context into prompts without the LLM calling a function.
Q: Can one MCP server expose multiple types of primitives?
Yes. A single server can provide tools, resources, and prompts. The host discovers each type independently and can use them in combination. For example, a calendar server might expose a create_event tool, a today_schedule resource, and a summarize_day prompt.
Test yourself
You are extending the personal assistant with a weather MCP server that provides a get_forecast tool. The server is local and communicates over stdio. Describe the full flow from host startup to the assistant answering a user’s question about the weather in Berlin.
Answer: The host creates an MCP client for the weather server and launches it as a child process. The client sends an initialize request with its protocol version and capabilities. The server responds with its own version and features. The client sends an initialized notification. The host then calls tools/list through the client, discovering the get_forecast tool with parameters location and units. The host converts this into a tool definition for the LLM. When the user asks, “What’s the weather in Berlin?”, the LLM emits a tool call for get_forecast with {"location": "Berlin", "units": "metric"}. The host maps this to a tools/call request via the client. The server receives the request, calls an external weather API, and returns a structured result with temperature and conditions. The host injects that result into the LLM’s context. The LLM then generates a natural language answer: “It’s 22°C and partly cloudy in Berlin.”
If you want this kind of breakdown every week, how real systems actually work under the hood, subscribe to Internals Decoded at internalsdecoded.com.
Sources
- MCP Specification
- MCP Architecture Overview
- MCP Authorization
- Anthropic MCP Announcement
- LangChain MCP Adapter
- GitHub MCP Server
- Filesystem MCP Server
- MCP SDKs