- Basic (stdio)
- Advanced
Basic calculator server
Located at03-GettingStarted/samples/python, this is a minimal MCP server with four calculator tools.Clone and navigate
git clone https://github.com/microsoft/mcp-for-beginners.git
cd mcp-for-beginners/03-GettingStarted/samples/python
Run the server
python mcp_calculator_server.py
When run directly in a terminal you will see JSON-RPC validation errors — this is expected. The server waits for properly formatted MCP client messages on stdin.
Server code
mcp_calculator_server.py
#!/usr/bin/env python3
"""Sample MCP Calculator Server implementation in Python."""
from mcp.server.fastmcp import FastMCP
# Create a FastMCP server
mcp = FastMCP("Calculator MCP Server")
@mcp.tool()
def add(a: float, b: float) -> float:
"""Add two numbers together and return the result."""
return a + b
@mcp.tool()
def subtract(a: float, b: float) -> float:
"""Subtract b from a and return the result."""
return a - b
@mcp.tool()
def multiply(a: float, b: float) -> float:
"""Multiply two numbers together and return the result."""
return a * b
@mcp.tool()
def divide(a: float, b: float) -> float:
"""
Divide a by b and return the result.
Raises:
ValueError: If b is zero
"""
if b == 0:
raise ValueError("Cannot divide by zero")
return a / b
if __name__ == "__main__":
mcp.run()
Test script
test_calculator.py
from mcp_calculator_server import add, subtract, multiply, divide
def test_calculator_functions():
assert add(5, 3) == 8
print("Addition: OK")
assert subtract(10, 4) == 6
print("Subtraction: OK")
assert multiply(7, 6) == 42
print("Multiplication: OK")
assert divide(15, 3) == 5
print("Division: OK")
try:
divide(10, 0)
except ValueError as e:
assert str(e) == "Cannot divide by zero"
print("Divide-by-zero guard: OK")
test_calculator_functions()
Advanced server + client pair
Located at04-PracticalImplementation/samples/python, this sample demonstrates all three MCP primitives — tools, resources, and prompts — along with a matching async client.Start the server (terminal 1)
python server.py
mcp dev server.py
Server code
from mcp.server.fastmcp import FastMCP
import logging, json
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)
AVAILABLE_MODELS = ["gpt-4", "llama-3-70b", "claude-3-sonnet"]
mcp = FastMCP("Python MCP Demo Server")
@mcp.tool()
def completion(model: str, prompt: str, temperature: float = 0.7, max_tokens: int = 100) -> str:
"""Generate completions using AI models."""
if model not in AVAILABLE_MODELS:
raise ValueError(f"Model {model} not supported")
return f"Simulated response to: {prompt[:30]}..."
@mcp.tool()
def add(a: int, b: int) -> int:
"""Add two numbers together."""
logger.info(f"Adding {a} and {b}")
return a + b
Client code
client.py
import asyncio, json, urllib.parse
from mcp import ClientSession, StdioServerParameters
from mcp.client.stdio import stdio_client
from mcp.types import TextContent, TextResourceContents
async def main():
server_params = StdioServerParameters(command="python", args=["server.py"])
async with stdio_client(server_params) as (reader, writer):
async with ClientSession(reader, writer) as session:
await session.initialize()
# 1. Call the add tool
result = await session.call_tool("add", arguments={"a": 5, "b": 7})
print(f"5 + 7 = {result.content[0].text}")
# 2. Call the completion tool
comp = await session.call_tool(
"completion",
arguments={"model": "gpt-4", "prompt": "What is the meaning of life?"}
)
print(f"Completion: {comp.content[0].text}")
# 3. Read the models resource
models_resp = await session.read_resource("models://")
models = json.loads(models_resp.contents[0].text)
for m in models["models"]:
print(f" - {m['name']}")
# 4. Read a greeting resource
name = urllib.parse.quote("MCP Explorer")
greeting = await session.read_resource(f"greeting://{name}")
print(greeting.contents[0].text)
# 5. Use the code review prompt
prompt = await session.get_prompt(
"review_code",
{"code": "def hello():\n print('hi')"}
)
print(prompt.messages[0].content.text)
asyncio.run(main())
What this sample demonstrates
| Primitive | Example |
|---|---|
| Tool | add(a, b) — callable function with return value |
| Tool | completion(model, prompt) — simulated AI model call |
| Resource | models:// — static data exposed as a URI |
| Resource | greeting://{name} — dynamic resource with URI template parameter |
| Prompt | review_code(code) — reusable prompt template |