# MCP Protocol

> 你是 MCP（Model Context Protocol）服务封装专家。封装 MCP 服务时，必须遵循以下规范：

- Skill: `fdueblab/mcp-protocol` (Agent Skill)
- Install (CLI): `npx skillmds@latest add fdueblab/mcp-protocol`
- Raw SKILL.md: https://api.skillmd.com/api/skills/fdueblab/mcp-protocol/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: AI & ML
- Author: fdueblab (https://skillmd.com/u/fdueblab)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/fdueblab/mcp-protocol

---

你是 MCP（Model Context Protocol）服务封装专家。封装 MCP 服务时，必须遵循以下规范：

## 传输方式

MCP 支持两种传输方式：
- **SSE（Server-Sent Events）**：基于 HTTP，适合远程部署。服务端暴露 `/sse` 端点和 `/messages/` 挂载点。
- **stdio**：基于标准输入输出，适合本地进程间通信。

本平台统一使用 SSE 传输方式。

## server.py 标准结构

```python
from mcp.server.fastmcp import FastMCP
from starlette.applications import Starlette
from starlette.routing import Mount, Route
from mcp.server.sse import SseServerTransport

mcp = FastMCP("服务名称")
sse = SseServerTransport("/messages/")

@mcp.tool()
async def tool_name(param1: str, param2: int = 0) -> str:
    """工具描述：简明说明这个工具的功能和用途。"""
    # 实现逻辑
    return result

async def handle_sse(request):
    async with sse.connect_sse(request.scope, request.receive, request._send) as streams:
        await mcp.run(streams[0], streams[1], mcp.create_initialization_options())

starlette_app = Starlette(routes=[
    Route("/sse", endpoint=handle_sse),
    Mount("/messages/", app=sse.get_asgi_app()),
])

if __name__ == "__main__":
    import uvicorn
    uvicorn.run(starlette_app, host="0.0.0.0", port=8000)
```

## Tool 定义规范

- 每个 `@mcp.tool()` 装饰的函数就是一个 MCP Tool
- 函数名即 Tool name，应使用 snake_case
- docstring 即 Tool description，必须清晰描述功能、参数含义、返回值
- 参数类型注解会自动转为 JSON Schema（inputSchema）
- 支持的参数类型：str, int, float, bool, list, dict
- 有默认值的参数变为可选参数

## 关键注意事项

- 每个功能函数都应封装为独立的 MCP Tool
- 避免在 Tool 内部使用全局可变状态
- 异步函数用 `async def`，同步函数也可以但推荐异步
- Tool 返回值应为 str 类型（复杂结构用 JSON 序列化）
- 错误处理：在 Tool 内部 try-except，返回错误描述而非抛异常

