使用说明
MCP服务器蓝图
构建生产就绪MCP服务器的蓝图 FastMCP.
先决条件
- Python 3.14+
- 紫外线 包管理器
安装
uv sync
配置
cp .env.example .env
运行服务器
make serve
# or: uv run mcp-server-blueprint
服务器启动于 http://127.0.0.1:8000 默认情况下。MCP端点位于 /mcp (流式HTTP传输)。
要绑定到所有接口(例如Docker内部):
MCP_SERVER_HOST=0.0.0.0 make serve
发展
make check # lint + typecheck + tests + security audit (full quality gate)
make test # tests with coverage report only
make lint # ruff check
make format # ruff check --fix + ruff format
make typecheck # ty check
make audit # pip-audit vulnerability scan
项目结构
src/mcp_server_blueprint/
├── main.py # Entry point (logging + mcp.run)
├── server.py # FastMCP instance, lifespan, AppContext
├── config.py # Pydantic-settings configuration with validators
├── errors.py # Custom error types
├── descriptions.py # Description strings for all tools, resources, and prompts
├── params.py # Annotated type aliases with validation constraints
├── shared.py # handle_errors decorator
├── tools.py # MCP tools
├── resources.py # MCP resources (static + template)
├── prompts.py # MCP prompt templates
└── infrastructure/
└── http_client.py # Async HTTP client with timeout and auth
延伸
这三个共享模块使处理程序完全专注于业务逻辑:
descriptions.py--人类可读的描述传递给@mcp.tool(description=...),对AI客户端可见params.py—Annotated同时携带验证约束的类型别名(PydanticField,StringConstraints)JSON模式的字段描述shared.py—@handle_errors捕获任何未处理的异常并返回结构化{"error": ..., "status_code": ...}JSON响应,通过日志记录ctx.error当上下文可用时
添加工具
descriptions.py
YOUR_TOOL = "What the tool does, as seen by the AI client."
params.py
YourParam = Annotated[str, StringConstraints(strip_whitespace=True, min_length=1), Field(description="...")]
tools.py
from .descriptions import YOUR_TOOL
from .params import YourParam
from .server import AppContext, mcp
from .shared import handle_errors
@mcp.tool(description=YOUR_TOOL)
@handle_errors
async def your_tool(ctx: Context, param: YourParam) -> str:
app: AppContext = ctx.request_context.lifespan_context
response = await app.http(ctx).get(f"/endpoint/{param}")
return json.dumps(response, indent=2)
app.http(ctx) 返回a HttpClient 通过预先绑定请求的承载令牌,令牌传递可以自动工作,无需任何额外的连接。
添加资源
# descriptions.py
YOUR_RESOURCE = "What the resource exposes."
# resources.py
@mcp.resource("scheme://{param}", description=YOUR_RESOURCE)
@handle_errors
async def your_resource(param: YourParam, ctx: Context) -> str:
app: AppContext = ctx.request_context.lifespan_context
response = await app.http(ctx).get(f"/endpoint/{param}")
return json.dumps(response, indent=2)
添加提示
# descriptions.py
YOUR_PROMPT = "What the prompt template does."
# prompts.py
@mcp.prompt(description=YOUR_PROMPT)
def your_prompt(param: YourParam) -> str:
return f"Use the your_tool tool with param '{param}' and summarize the result."
许可证
麻省理工学院
