MCP

MCP Servers👨‍💻

An MCP server is a program that exposes capabilities -- tools, resources, and prompts -- to AI applications over the Model Context Protocol. Servers are the supply side of the protocol: they advertise what they can do during the initialization handshake and then respond to requests from clients. The official SDKs for TypeScript (@modelcontextprotocol/sdk) and Python (mcp) provide high-level abstractions that handle the protocol plumbing so you can focus on your domain logic. In TypeScript you use the McpServer class with registerTool and registerResource methods; in Python you use the FastMCP class with @mcp.tool() and @mcp.resource() decorators. Both SDKs support stdio, SSE, and Streamable HTTP transports out of the box.

Key Takeaways

  • 1The TypeScript SDK provides the McpServer class from @modelcontextprotocol/server. You create an instance with a name and version, register tools and resources, then connect it to a transport (StdioServerTransport for local, NodeStreamableHTTPServerTransport for remote).
  • 2The Python SDK provides the FastMCP class from mcp.server.fastmcp. Tools, resources, and prompts are defined using decorators (@mcp.tool(), @mcp.resource(), @mcp.prompt()), and the server is started with mcp.run() specifying the transport.
  • 3The server lifecycle follows a strict sequence: the client sends an initialize request, the server responds with its capabilities and info, the client sends a notifications/initialized notification, and then normal request-response communication begins.
  • 4Servers declare their capabilities during initialization. A server that only exposes tools will declare { tools: {} } in its capabilities. This tells the client not to attempt resource reads or prompt requests against this server.
  • 5For production deployments, the Streamable HTTP transport is recommended. It supports session management, multiple concurrent clients, and works behind standard HTTP infrastructure (load balancers, reverse proxies, authentication middleware).
  • 6Both SDKs handle JSON-RPC serialization, request routing, and error formatting automatically. You write plain functions that return results, and the SDK wraps them in the correct JSON-RPC response format.

Examples

Basic MCP server in TypeScript with stdio transport

typescript

This is the minimal structure for a TypeScript MCP server. The McpServer instance manages capability declaration and request routing. registerTool takes a name, metadata with a Zod input schema, and an async handler. StdioServerTransport connects via stdin/stdout, which is ideal for local process-spawned servers. Note that logs go to stderr because stdout is reserved for protocol messages.

Basic MCP server in Python with FastMCP

python

The Python SDK uses decorators for a concise, Pythonic API. The @mcp.tool() decorator registers a function as a tool, using the function name as the tool name and the docstring as the description. Type hints on the function parameters are automatically converted to the JSON Schema input definition. mcp.run() starts the server on stdio by default.

TypeScript MCP server with Streamable HTTP transport

typescript

For production deployments, Streamable HTTP supports session management and concurrent clients. Each initialize request creates a new session with a unique ID. Subsequent requests include the session ID in headers to route to the correct transport. This approach integrates naturally with Express middleware for authentication, rate limiting, and logging. For a shipped example of this pattern, Web Anatomy runs a token-authenticated MCP server over Streamable HTTP, exposing its landing-page benchmark library (search_sections, search_pages, get_section, get_page, plus list_filters and health) to any MCP-compatible client.

Python MCP server with Streamable HTTP transport

python

Switching transports in the Python SDK is a one-line change. Setting transport to streamable-http starts an HTTP server that handles session management automatically. The json_response=True option tells FastMCP to serialize return values as JSON, which is useful when tools return structured data like dictionaries or lists.

Installing and running an MCP server with npx or uvx

bash

MCP servers can be distributed as npm or PyPI packages and run without permanent installation using npx or uvx. AI hosts like Claude Desktop use a JSON configuration file to specify which servers to launch. Each server entry defines the command to run and the arguments to pass, and the host manages the server lifecycle automatically.

Common Mistakes

Mistake:

Logging output to stdout in a stdio-transport server, which corrupts the JSON-RPC message stream and causes protocol errors.

Fix:

Always log to stderr (console.error in Node.js, print to sys.stderr in Python) when using stdio transport. Stdout is exclusively reserved for protocol messages.

Mistake:

Creating a single server instance that handles multiple concurrent HTTP sessions, leading to shared state and race conditions.

Fix:

Create a new McpServer instance per session when using Streamable HTTP transport. The factory pattern (a createServer function called for each new session) ensures complete isolation between clients.

Mistake:

Not handling server shutdown gracefully, leaving orphaned connections or resources open when the process exits.

Fix:

Listen for process signals (SIGINT, SIGTERM) and call server.close() or transport.close() to cleanly shut down. In HTTP mode, also clean up session state on connection close.

Mistake:

Forgetting to set the name and version in the McpServer constructor, causing clients to receive empty server info during initialization.

Fix:

Always provide a descriptive name and semantic version when creating the server. Clients use this information for logging, debugging, and compatibility checks.

Mistake:

Returning raw strings from Python tool handlers instead of structured content, causing the client to receive improperly formatted responses.

Fix:

For simple text responses, return a plain string -- FastMCP wraps it in the correct content format. For structured data, use json_response=True on the FastMCP instance or return a dict/list, and FastMCP will serialize it as JSON text content.

Best Practices

  • Use stdio transport for development and local integrations (CLI tools, desktop apps). Switch to Streamable HTTP for production servers that need to handle multiple clients, support authentication, or run behind load balancers.
  • Keep your server focused on a single domain. A file-system server should handle file operations; a database server should handle queries. Composing multiple focused servers is better than building one monolithic server.
  • Use Zod schemas (TypeScript) or Python type hints to define tool inputs. The SDKs convert these to JSON Schema automatically, and the type information helps AI models construct valid arguments.
  • Implement health checks for HTTP-transport servers. A simple GET /health endpoint lets infrastructure tools (Kubernetes, load balancers) verify the server is running without initiating an MCP session.
  • Test your server with the official MCP Inspector tool (npx @modelcontextprotocol/inspector). It provides an interactive UI for calling tools, reading resources, and verifying protocol compliance without needing a full AI host.
  • Pin your SDK dependency versions. Both the TypeScript and Python SDKs are actively developed, and breaking changes can occur between major versions. Use exact versions in package.json or requirements.txt.

Summary

MCP servers are programs that expose tools, resources, and prompts to AI applications over the Model Context Protocol. The TypeScript SDK provides McpServer with registerTool and registerResource methods, while the Python SDK provides FastMCP with decorator-based registration. Servers follow a strict lifecycle: initialize handshake, capability negotiation, then request-response communication. Use stdio transport for local development and Streamable HTTP for production. Both SDKs handle JSON-RPC serialization, error formatting, and transport management, letting you focus on your domain logic.

Practice MCP with hands-on challenges

Learn mcp servers hands-on in your IDE

Interactive lessons and challenges on Stanza, practice in VS Code, Cursor, or the web.

Related Concepts

Related Cheatsheets

Master MCP with Stanza

Interactive lessons and challenges, right in your code editor.

Check the free courses. No credit card.