学生记录MCP服务器
功能齐全 模型上下文协议(MCP) 内置Python的服务器,用于管理学生记录系统。任何兼容MCP的AI客户端(Claude Desktop、VS Code Copilot、MCP Inspector)都可以使用自然语言调用其工具。
______________________________________________________________________
目录
______________________________________________________________________
1.什么是MCP?
MCP(模型上下文协议) 是由Anthropic创建的开放标准,允许AI模型以结构化、安全的方式调用外部工具和访问数据源。将其视为人工智能的通用插件系统——你通过标准协议公开工具,任何兼容的人工智能客户端都可以使用它们。
AI Client (Claude / VS Code Copilot)
│
│ JSON-RPC over stdio or HTTP
▼
MCP Server (server.py)
│
│ Python function calls
▼
Database Layer (database.py + SQLite)
│
▼
students.db______________________________________________________________________
2.项目要求
学生属性
| 字段 | 类型 | 注释 |
|---|---|---|
| student_id | 文本 | 主键 |
| 名称 | 文本 | 全名 |
| 电子邮件 | 文本 | 唯一 |
| 兴趣 | 文本 | 逗号分隔 |
| home_location | 文本 | 城市和国家 |
| 等级 | TEXT | A、B+等。 |
课程属性
| 字段 | 类型 | 注释 |
|---|---|---|
| course_id | 整数 | 自动递增PK |
| 名称 | 文本 | 唯一 |
| 领域 | 文本 | 技术、科学、艺术、商业 |
| term_years | REAL | 十进制持续时间 |
注册属性(连接表)
| 字段 | 类型 | 注释 |
|---|---|---|
| student_name | 文本 | 引用学生 |
| course_name | 文本 | 参考课程 |
| 注册_开始 | 文本 | 格式:YYYY-MM-DD |
| enrollment_end | TEXT | 可为空 |
| 课程已完成 | INTEGER | 0=否,1=是 |
MCP工具
| 工具 | 目的 |
|---|---|
get_student | 按ID检索学生 |
add_student | 插入新的学生记录 |
search_student | 按姓名/电子邮件/地点/兴趣搜索 |
enroll_student | 为学生注册课程(连接表) |
courses_available | 列出所有可用课程 |
add_course | 插入新课程 |
search_course | 按名称或域搜索课程 |
______________________________________________________________________
3.系统架构
!\[正在上传mcp\_
MCP Client Claude / AI Host
MCP Server -->
stdio/SSE
MCP Server server.py FastMCP / mcp SDK
Tools -->
Tool Handlers 7 registered tools
DB Layer -->
DB Access SQLite + seed data
SQLite -->
students.db
获取·添加·搜索·注册 课程·添加课程·搜索课程
Project Files server.py database.py seed_data.py
DB Tables students courses student_courses
步骤1–2 第3-5步 步骤2 步骤1 student_records_architecture.svg…\]()
┌─────────────────────────────────────────────────────────┐
│ AI CLIENT LAYER │
│ Claude Desktop │ VS Code Copilot │ Inspector │ curl │
└───────────────────────────┬─────────────────────────────┘
│
stdio (local) │ HTTP POST /mcp (network)
│
┌───────────────────────────▼─────────────────────────────┐
│ MCP SERVER LAYER │
│ server.py → FastMCP instance → @mcp.tool() handlers │
└───────────────────────────┬─────────────────────────────┘
│
Python function calls
│
┌───────────────────────────▼─────────────────────────────┐
│ DATABASE ACCESS LAYER │
│ database.py → get_connection() → sqlite3 queries │
└───────────────────────────┬─────────────────────────────┘
│
SQL
│
┌───────────────────────────▼─────────────────────────────┐
│ DATA LAYER │
│ students.db │
│ ├── students │
│ ├── courses │
│ └── student_courses (junction) │
└─────────────────────────────────────────────────────────┘数据库模式
CREATE TABLE students (
student_id TEXT PRIMARY KEY,
name TEXT NOT NULL,
email TEXT UNIQUE NOT NULL,
interests TEXT,
home_location TEXT,
grade TEXT
);
CREATE TABLE courses (
course_id INTEGER PRIMARY KEY AUTOINCREMENT,
name TEXT UNIQUE NOT NULL,
domain TEXT NOT NULL,
term_years REAL NOT NULL
);
CREATE TABLE student_courses (
id INTEGER PRIMARY KEY AUTOINCREMENT,
student_name TEXT NOT NULL,
course_name TEXT NOT NULL,
enrollment_start TEXT NOT NULL,
enrollment_end TEXT,
course_completed INTEGER NOT NULL DEFAULT 0,
UNIQUE(student_name, course_name) -- prevents duplicate enrollment
);______________________________________________________________________
4.文件结构
student-mcp-server/
├── server.py # MCP server — FastMCP instance + all 7 tools
├── database.py # Schema DDL + get_connection() helper
├── seed_data.py # Dummy data — 5 students, 8 courses, 6 enrollments
├── students.db # Auto-created SQLite database
├── test_server.py # Python HTTP test client (handles session ID)
├── cleanup.sh # Kill stuck MCP ports (macOS/Linux)
├── cleanup.ps1 # Kill stuck MCP ports (Windows)
└── .vscode/
├── mcp.json # VS Code MCP server config
├── tasks.json # VS Code tasks (seed, inspector, cleanup)
└── launch.json # Debug configs______________________________________________________________________
5.设置和安装
第一步——创建项目和虚拟环境
mkdir student-mcp-server
cd student-mcp-server
python -m venv venv
# Activate venv
source venv/bin/activate # macOS/Linux
venv\Scripts\activate # Windows步骤2--安装依赖项
pip install mcp fastmcp uvicorn starlette httpx
pip install "mcp[cli]" # MCP CLI + Inspector
# Verify
pip show mcp
mcp --version步骤3——为数据库添加种子
python seed_data.py
# Output: Database seeded successfully.
# Creates students.db with 5 students, 8 courses, 6 enrollments步骤4--运行服务器
# stdio mode (Claude Desktop / VS Code)
python server.py
# Streamable HTTP (auto port detection)
python server.py --transport streamable-http
# Streamable HTTP on specific port
python server.py --transport streamable-http --port 8080______________________________________________________________________
6.MCP传输类型
| 运输 | 代码 | 最适合 |
|---|---|---|
| 标准 | mcp.run(transport="stdio") | 本地开发,克劳德桌面,VS代码——单客户端,同一台机器 |
| 上海证券交易所 | mcp.run(transport="sse") | MCP 1.6.x HTTP-较旧的API,终结点: /sse |
| 可流式传输的HTTP | mcp.run(transport="streamable-http") | 生产,多个客户,MCP 1.9+,端点: /mcp |
交通演变
stdio (2024) → SSE (2024, deprecated) → Streamable HTTP (2025, current)流式HTTP——会话流
POST /mcp initialize → server creates session
← mcp-session-id: abc123 (capture this!)
POST /mcp notifications/initialized
mcp-session-id: abc123 → session validated ✅
POST /mcp tools/call ...
mcp-session-id: abc123 → session validated ✅______________________________________________________________________
7.命令参考
MCP检查器命令
| 命令 | 它做什么 |
|---|---|
mcp dev server.py | 启动检查器UI(端口6274)+代理+服务器.py |
mcp --version | 检查已安装的MCP CLI版本 |
pip install "mcp[cli]" | 使用检查器安装MCP CLI |
pip install --upgrade mcp | 升级至最新MCP版本 |
pip show mcp | 显示安装版本和详细信息 |
端口管理(macOS/Linux)
# Kill a specific port
lsof -ti:6274 | xargs kill -9
lsof -ti:6277 | xargs kill -9
lsof -ti:8000 | xargs kill -9
# Kill all MCP ports at once
lsof -ti:6274,6277,3000,8000 | xargs kill -9
# Check if port is free (no output = free)
lsof -i:8000端口管理(Windows PowerShell)
# Find process on port
netstat -ano | findstr :8000
# Kill by PID
taskkill /PID
/Fstdio JSON-RPC测试命令
始终发送 initialize 首先,然后是任何工具调用。
# 1. Initialize
echo '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2024-11-05","clientInfo":{"name":"test","version":"1.0"},"capabilities":{}}}
{"jsonrpc":"2.0","method":"notifications/initialized","params":{}}' | python server.py
# 2. List tools
{"jsonrpc":"2.0","id":2,"method":"tools/list","params":{}}
# 3. get_student
{"jsonrpc":"2.0","id":3,"method":"tools/call","params":{"name":"get_student","arguments":{"student_id":"STU001"}}}
# 4. search_student
{"jsonrpc":"2.0","id":4,"method":"tools/call","params":{"name":"search_student","arguments":{"query":"London"}}}
# 5. courses_available
{"jsonrpc":"2.0","id":5,"method":"tools/call","params":{"name":"courses_available","arguments":{}}}
# 6. search_course
{"jsonrpc":"2.0","id":6,"method":"tools/call","params":{"name":"search_course","arguments":{"query":"science"}}}
# 7. add_student
{"jsonrpc":"2.0","id":7,"method":"tools/call","params":{"name":"add_student","arguments":{"student_id":"STU006","name":"Leo Tan","email":"leo@example.com","interests":"Cloud","home_location":"Singapore","grade":"A"}}}
# 8. enroll_student
{"jsonrpc":"2.0","id":8,"method":"tools/call","params":{"name":"enroll_student","arguments":{"student_name":"Leo Tan","course_name":"Machine Learning 101","enrollment_start":"2025-09-01"}}}用于流式HTTP的curl命令
# Initialize — use -v to see mcp-session-id in response headers
curl -v -X POST http://localhost:8000/mcp \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2024-11-05","capabilities":{},"clientInfo":{"name":"curl-test","version":"1.0"}}}'
# All subsequent calls — include session ID
curl -X POST http://localhost:8000/mcp \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-H "mcp-session-id: " \
-d '{"jsonrpc":"2.0","id":2,"method":"tools/list","params":{}}'Python自检命令
# Check what your MCP version accepts in run()
python -c "from mcp.server.fastmcp import FastMCP; help(FastMCP.run)"
# Check FastMCP constructor parameters
python -c "from mcp.server.fastmcp import FastMCP; help(FastMCP.__init__)"
# Get MCP version
python -c "import mcp; print(mcp.__version__)"
# Get absolute paths for config files
which python # macOS/Linux
where python # Windows
realpath server.py # macOS/Linux
echo %cd%\server.py # Windows
# Collapse multi-line JSON to single line
echo '{...}' | jq -c .
echo '{...}' | python -m json.tool
# Pretty print compressed JSON response
echo '{...}' | python -m json.tool______________________________________________________________________
8.MCP检查员指南
键入时运行什么 mcp dev server.py
mcp dev server.py
│
├──► Process 1: Inspector UI → port 6274 (React web app)
├──► Process 2: Proxy Server → port 6277 (HTTP ↔ stdio bridge)
└──► Process 3: server.py → stdin/stdout (spawned on Connect click)MCP_PROXY_AUTH_TOKEN
- 使用生成
secrets.token_hex(32)--64个十六进制字符,256位随机性 - 嵌入到检查器URL中
?token=abc123... - 发送方式
x-mcp-proxy-token每个浏览器上的标题→代理请求 - 已通过验证
hmac.compare_digest()--恒定时间,防止计时攻击 - 仅存在于进程内存中,从不写入磁盘
- 被摧毁了
Ctrl+C--每次推出新代币
检查员连接表
| 字段 | 值 | 注释 |
|---|---|---|
| 运输类型 | STDIO | 用于本地开发 |
| 指挥部 | /path/to/venv/bin/python | 必须是绝对路径 |
| 论点 | /path/to/server.py | 必须是绝对路径 |
| 环境变量 | FASTMCP_PORT=8000 | 可选键=值对 |
| URL(HTTP模式) | http://localhost:8000/mcp | 用于流式HTTP传输 |
带空格的路径:使用Arguments字段并将路径括在双引号中,或将项目移动到没有空格的路径(例如。 C:\projects\student-mcp-server).如何捕获原始JSON-RPC
| 方法 | 如何 |
|---|---|
| 检查器历史面板 | UI底部--单击任何条目 |
| 浏览器DevTools网络 | F12→ 网络→ 过滤器 localhost:3000 → 有效载荷/响应选项卡 |
| 控制台获取拦截器 | 将JS拦截脚本粘贴到DevTools控制台中 |
| 服务器端日志文件 | 添加 logging 到server.py→ tail -f mcp_trace.log |
克劳德桌面/MCP检查员 │ │ 作为子进程生成 ▼ 服务器.py │ │ 通过stdin/stdout进行通信 ▼ JSON-RPC消息
9.VS代码集成
需求
- VS代码 1.99或更高版本
- GitHub Copilot聊天扩展已安装并登录
.vscode/mcp.json
{
"servers": {
"student-records": {
"type": "stdio",
"command": "${workspaceFolder}/venv/bin/python",
"args": ["${workspaceFolder}/server.py"],
"env": {}
}
}
}${workspaceFolder} 自动解析为您的绝对项目路径——处理空格,无需硬编码。Windows版本:
{
"servers": {
"student-records": {
"type": "stdio",
"command": "${workspaceFolder}\\venv\\Scripts\\python.exe",
"args": ["${workspaceFolder}\\server.py"],
"env": {}
}
}
}如何使用
- 按
Ctrl+Alt+I打开Copilot聊天 - 切换到 代理 面板底部的模式
- 点击工具图标——确认所有7个工具都已选中
- 键入自然语言——Copilot会自动调用正确的工具
示例提示
"Get me the details for student STU001"
"Find all students from London"
"Add a new student named Marco Rossi, email marco@example.com, ID STU011, grade B+"
"What courses are available?"
"Show me all science courses"
"Enroll Alice Chen in Data Structures starting 2025-09-01"
"Find all technology courses then enroll Alice in Data Structures"验证连接
Ctrl+Shift+P → MCP: List Servers # should show: student-records Running
View → Output → MCP: student-records # raw JSON-RPC logs
Ctrl+Shift+P → MCP: Restart Server # if stuck______________________________________________________________________
10.错误参考
连接错误
| 错误 | 根本原因 | 解决方案 | |
|---|---|---|---|
Connection Error — proxy token incorrect | 跑步 server.py 分开之前 mcp dev,或缺少URL ?token= | 停下 server.py.仅运行: mcp dev server.py.从终端复制包括令牌在内的完整URL | |
Inspector PORT IS IN USE at localhost:6274 | 用X而不是Ctrl+C关闭终端——进程仍在运行 | `lsof -ti:6274 \ | xargs kill -9` |
Proxy Server PORT IS IN USE at port 6277 | 来自上一个会话持有端口的代理 | `lsof -ti:6274,6277,3000,8000 \ | xargs kill -9` |
[Errno 48] address already in use (port 8000) | 上一页 python server.py 仍在运行 | `lsof -ti:8000 \ | xargs kill -9` |
API/版本错误
| 错误 | 根本原因 | 解决方案 |
|---|---|---|
TypeError: FastMCP.run() got unexpected keyword argument 'host' | MCP 1.6.x——主机/端口进入构造函数或环境变量,不进入 run() | 设置 os.environ["FASTMCP_HOST"] 和 FASTMCP_PORT 之前 FastMCP().致电 mcp.run(transport="streamable-http") 没有其他参数 |
mcp command not found | MCP CLI未安装或venv未激活 | source venv/bin/activate 然后 pip install "mcp[cli]" |
HTTP/协议错误
| 错误 | 根本原因 | 解决方案 |
|---|---|---|
{"error":{"code":-32600,"message":"Not Acceptable: Client must accept both..."}} | curl缺少Accept标头--流式HTTP需要两种MIME类型 | 添加 -H "Accept: application/json, text/event-stream" 每卷 |
missing session ID | 流式HTTP是无状态的——每个请求都需要 mcp-session-id | 捕获 mcp-session-id 从初始化响应标头(curl -v).发送方式 -H "mcp-session-id: VALUE" 在所有后续请求中 |
404 Not Found on http://localhost:8000/ | 根URL没有处理程序——只有 /mcp 存在 | 使用 http://localhost:8000/mcp 对于所有请求 |
405 Method Not Allowed on GET /mcp | MCP端点需要POST--不支持GET | 这是正确的,也是意料之中的 --确认端点存在。使用POST |
Inspector form blank / not pre-filled | 打开的URL没有查询参数,或者路径中断URL编码中有空格 | 使用终端中的精确URL。运行: mcp dev "$(pwd)/server.py" |
数据错误
| 错误 | 根本原因 | 解决方案 |
|---|---|---|
UNIQUE constraint failed: student_courses | 让学生注册他们已经注册的课程 | 预期行为——防止重复工作。退货 success: false |
No student found with ID 'STU001' | 错误的学生ID或DB未播种 | 运行 python seed_data.py 首先 |
______________________________________________________________________
11.快速参考卡
使用的所有端口
| 端口 | 服务 | 终止(macOS/Linux) | |
|---|---|---|---|
| 6274 | MCP检查器用户界面 | `lsof -ti:6274 \ | xargs kill -9` |
| 6277 | MCP代理服务器 | `lsof -ti:6277 \ | xargs kill -9` |
| 3000 | MCP代理(旧版) | `lsof -ti:3000 \ | xargs kill -9` |
| 8000 | 流式HTTP | `lsof -ti:8000 \ | xargs kill -9` |
JSON-RPC消息结构
// Request
{
"jsonrpc": "2.0", // always 2.0
"id": 1, // integer — matches response to request
"method": "tools/call", // initialize | tools/list | tools/call
"params": {
"name": "get_student", // tool name
"arguments": { // tool inputs
"student_id": "STU001"
}
}
}
// Response
{
"jsonrpc": "2.0",
"id": 1, // matches request id
"result": {
"content": [{
"type": "text",
"text": "{\"student_id\": \"STU001\", ...}"
}]
}
}虚假数据——学生
| ID | 名称 | 地点 | 等级 |
|---|---|---|---|
| STU001 | Alice Chen | 加利福尼亚州旧金山 | A |
| STU002 | 鲍勃·马丁 | 德克萨斯州奥斯汀 | B+ |
| STU003 | 克拉拉·奥塞 | 英国伦敦 | A- |
| STU004 | 金大卫 | 韩国首尔 | B |
| STU005 | 伊娃·罗西 | 意大利罗马 | A+ |
虚拟数据——课程
| 名称 | 域名 | 术语 |
|---|---|---|
| 机器学习101 | 技术 | 1.0年 |
| Web开发训练营 | 技术 | 0.5年 |
| 生物学基础 | 科学 | 2.0年 |
| 艺术史 | 艺术 | 1.0年 |
| 量子物理学 | 科学 | 2.0年 |
| 音乐理论 | 艺术 | 1.5年 |
| 数据结构 | 技术 | 1.0年 |
| 数字营销 | 商业 | 0.5年 |
日常工作流程
# 1. Navigate and activate
cd student-mcp-server
source venv/bin/activate
# 2a. Inspector testing
mcp dev server.py
# Open URL from terminal (includes token), connect, use Tools tab
# 2b. Streamable HTTP testing
python server.py --transport streamable-http
# Inspector: Transport = Streamable HTTP, URL = http://localhost:8000/mcp
# 2c. VS Code — just open chat in Agent mode, server auto-starts
# 3. If ports are stuck
lsof -ti:6274,6277,3000,8000 | xargs kill -9
./cleanup.sh运输比较
| 因素 | stdio | 可流式HTTP |
|---|---|---|
| 克劳德桌面 | ✅ 必填 | ❌ 还没有 |
| VS代码副本 | ✅ 是 | ✅ 是的 |
| 多个客户端 | ❌ 只有一个 | ✅ 许多 |
| 部署到服务器 | ❌ 否 | ✅ 是的 |
| 需要会话ID | ❌ 否 | ✅ 是的 |
| 需要端口 | ❌ 否 | ✅ 是(8000) |
______________________________________________________________________
港口
在端口xxxx停止进程
lsof -ti :6277 | xargs kill -9验证它是否免费xxxx
lsof -ti :6277 | xargs kill -9按名称xxxx停止
pkill -f "mcp"
pkill -f "node"