What Is MCP and Why It Matters
Lesson 01 · MCP Servers · ~10 min read
Why MCP exists
The Model Context Protocol (MCP) was created to solve a specific scaling problem that anyone who tried to wire an LLM to real systems before 2024 ran into immediately: the M×N integration problem. You have M LLM-powered applications (Claude Desktop, Cursor, Windsurf, your own chat app, a CLI agent, a customer support bot) and N capabilities you want them to use (Slack search, GitHub issues, your team's wiki, a SQL database, the local filesystem). Without a shared protocol, every pair needs its own integration. That is M×N bespoke pieces of glue code — and every new client or every new capability multiplies the work.
Concretely: pre-MCP, if you wanted Claude Desktop to search Slack, you wrote a Slack-search shim in Claude Desktop's specific tool-calling format. Then a colleague wanted the same capability in Cursor, so they wrote a second Slack-search shim in Cursor's slightly different function-calling format. Then someone else built a CLI agent and wrote a third version. Three implementations of the same thing, each with its own bugs, each maintained separately, each broken in its own way when the Slack API changes.
MCP replaces this with a single common interface. Write the Slack server once; every MCP-aware client picks it up. The mental model is simple: MCP is to LLM tool use what HTTP is to web pages. HTTP doesn't render pages and it isn't a browser — it's the agreed protocol between many browsers and many servers that means each side only has to speak one dialect. MCP plays exactly the same role for the space between LLM apps and the tools, data, and prompts they want to reach.
The shape of an MCP server
An MCP server exposes three primitive kinds of capability. Each is small and focused; the power comes from how they compose. Understanding the difference between them is the single most important mental model in this course, because picking the wrong primitive is the most common beginner mistake.
- Tools — functions the LLM may call. Each tool is described by a JSON Schema declaring its name, what it does, and what arguments it accepts. When the model decides to invoke a tool, the client forwards the call to the server, which executes it and returns the result as text or as structured content blocks (text, images, embedded resources).
- Resources — read-only data identified by URI. Examples:
file:///notes/2026-05-21.md,sqlite:///users/42,github://issues/123. Resources are not invoked like tools; they are fetched by the client when relevant context is needed. The server publishes a catalog; the client decides when to pull a given resource into the model's context window. - Prompts — server-supplied prompt templates that the client can offer to the user, typically as a slash-command or menu option. They let a server ship recommended workflows ("summarize this PR", "draft a release note from these commits") so users don't have to remember the right prompt every time.
| Primitive | What it is | When to use | Example |
|---|---|---|---|
| Tool | Function the LLM calls | The model needs to do something (side effect, computation, query) | search_notes(query) |
| Resource | Read-only data at a URI | The client should pull context the model already knows it wants | file:///notes/2026-05-21.md |
| Prompt | Reusable prompt template | Surface a canned workflow to the user (slash command) | /summarize-pr |
Why a protocol beats one-off integrations
Three properties of MCP make it strictly better than the pre-MCP world, and together they explain why the ecosystem moved so fast in 2024–2025.
Reusability. Write a server once and every MCP-aware client picks it up. The filesystem server you build in this course works in Claude Desktop, Cursor, Windsurf, Cline, and any future client that speaks the protocol. No per-client port. No per-client bug-fixing. If Cursor ships a new release tomorrow, your server still works — the contract is the protocol, not the client.
User permissions live in the client, not the server. A server publishes the full list of things it could do; the client (and ultimately the user) decides which of those the model is actually allowed to invoke. This separation matters: the server author doesn't have to invent an auth UI, and the user gets one consistent permission surface across every server they install. Approving a tool call in Claude Desktop looks the same whether the underlying server is reading the filesystem, hitting Slack, or running shell commands.
Transport flexibility. The same MCP server runs unchanged over local stdio
(the client spawns it as a subprocess) or over remote HTTP (it lives behind a URL). You start local
for development, then move to HTTP for team-wide deployment without rewriting the server — only the
transport changes.
A fourth, more subtle property is sampling: a back-channel from the server to the LLM, mediated by the client. A server can ask the user's model to perform a piece of reasoning on its behalf — for example, summarizing a long document the server fetched. This means servers don't need to embed their own LLM; they can lean on whichever model the user is already paying for. It's the difference between an integration that ships its own brain and one that politely borrows the user's.
The 2026 landscape
As of mid-2026, MCP has moved from "interesting protocol from Anthropic" to a multi-vendor ecosystem.
Anthropic ships a set of reference servers covering the most common needs —
filesystem, fetch (HTTP requests), brave-search,
sqlite, github, slack, postgres, and others —
in the modelcontextprotocol/servers
repository. These are deliberately small and readable; reading their source is one of the best ways
to learn idiomatic MCP.
The community has added hundreds more: connectors for Notion, Linear, Jira, Google Drive, Kubernetes clusters, AWS, Stripe, and many domain-specific tools. Many ship as one-line installs through npm or pip.
Client adoption is what makes this matter. The major MCP-aware clients today include Claude Desktop (the reference client), Cursor, Windsurf, Cline, Zed, and several IDE extensions. Each of them lets a user point at a list of MCP servers and immediately use every tool those servers expose — without any client-specific configuration code.
The MCP registry — a central index of public servers with verification and version metadata — is the newest piece of the puzzle. At time of writing it is past initial release but still evolving rapidly; expect this paragraph to age faster than the rest of the lesson. Check the spec site for current status.
What this course builds
Over the next fifteen lessons you will build, deploy, and harden a real MCP server end to end. The running example is a Personal Knowledge Base (PKB) server: a small set of tools and resources for managing markdown notes, plus search, tagging, and a few useful prompt templates. It is small enough to fit in your head and rich enough to exercise every interesting feature of the protocol.
The arc is:
- Lessons 02–03 — the protocol up close. JSON-RPC framing, the handshake, message flow, what actually goes over stdio.
- Lessons 04–10 — building the PKB server in Python with the
official
mcpSDK. Tools first, then resources, then prompts, then sampling. - Lessons 11–15 — porting the same server to TypeScript and layering production concerns on top: auth, rate limiting, structured logging, deployment over HTTP, observability.
There is a working skeleton in mcp-servers/sample-server/ you can clone for any lesson
if you fall behind — every lesson builds on the previous one's state, so the skeleton lets you skip
forward without losing footing.
By the end you will have a server you would actually use, plus a clear sense of how to design new ones for whatever your team needs next.
Common pitfalls
- Confusing MCP servers with model-hosting servers. You are not running an LLM. You are providing tools to one. The model lives in the client (or behind it); your server just ships capabilities.
- Overusing prompts and resources when a tool would be clearer. If the model needs to do something with arguments, that's a tool. Resources are for data the client should pull in; prompts are for canned user-facing workflows. Reach for tools first.
- Starting on remote HTTP transport before mastering local stdio. Stdio is simpler, has no auth surface, and runs in two seconds. Build and debug locally; move to HTTP only once the server's logic is solid.
References
- MCP specification — the canonical protocol document.
- Python SDK —
github.com/modelcontextprotocol/python-sdk, used in lessons 04–10. - Official reference servers —
github.com/modelcontextprotocol/servers, an excellent source of idiomatic examples. claude/lesson13-building-mcp-server/— the preview lesson in the sibling Claude & LLMs course.