马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有账号?立即注册
×
FastMCP与FastAPI:构建自界说MCP服务器
模子上下文协议(Model Context Protocol, MCP)是一种让AI模子与外部工具和服务交互的标准。本文将先容FastMCP和FastAPI,并通过实例展示怎样创建自界说MCP服务器。
MCP基础概念
MCP答应语言模子:
- 访问外部工具和API
- 执行实时计算和查询
- 与文件体系和服务交互
简朴来说,MCP让AI模子能"走出"对话框,调用各种功能。
FastMCP先容
FastMCP是一个Python库,简化了MCP服务器的构建。它提供了:
- 易用的装饰器语法
- 自动处置惩罚哀求/相应
- 参数验证和错误处置惩罚
FastAPI先容
FastAPI是一个当代Web框架,用于构建API:
- 高性能(基于ASGI)
- 自动天生交互式文档
- 数据验证和序列化
- 基于Python范例提示
FastMCP与FastAPI的联合
二者联合的优势:
- FastAPI提供了Web服务器基础架构
- FastMCP添加了模子交互能力
- 共享相似的装饰器语法和范例体系
自界说MCP服务器示例
- # 示例1:基础计算器服务器
- from fastmcp import MCPServer, Request
- from fastapi import FastAPI
- from pydantic import BaseModel
- app = FastAPI()
- mcp_server = MCPServer(app)
- class CalculationRequest(BaseModel):
- x: float
- y: float
- @mcp_server.mcp_endpoint
- async def add(request: Request[CalculationRequest]) -> float:
- """将两个数字相加"""
- data = request.params
- return data.x + data.y
- @mcp_server.mcp_endpoint
- async def subtract(request: Request[CalculationRequest]) -> float:
- """从第一个数字中减去第二个数字"""
- data = request.params
- return data.x - data.y
- @mcp_server.mcp_endpoint
- async def multiply(request: Request[CalculationRequest]) -> float:
- """将两个数字相乘"""
- data = request.params
- return data.x * data.y
- @mcp_server.mcp_endpoint
- async def divide(request: Request[CalculationRequest]) -> float:
- """将第一个数字除以第二个数字"""
- data = request.params
- if data.y == 0:
- raise ValueError("除数不能为零")
- return data.x / data.y
- if __name__ == "__main__":
- import uvicorn
- uvicorn.run(app, host="0.0.0.0", port=8000)
- # 示例2:天气信息服务器
- from fastmcp import MCPServer, Request
- from fastapi import FastAPI
- from pydantic import BaseModel
- import random
- from datetime import datetime, timedelta
- app = FastAPI()
- mcp_server = MCPServer(app)
- class WeatherRequest(BaseModel):
- city: str
- days: int = 1
- class WeatherInfo(BaseModel):
- date: str
- temperature: float
- condition: str
- humidity: int
- @mcp_server.mcp_endpoint
- async def get_weather(request: Request[WeatherRequest]) -> list[WeatherInfo]:
- """获取指定城市的天气预报"""
- data = request.params
-
- # 这里使用模拟数据,实际应用中会调用真实的天气API
- weather_conditions = ["晴朗", "多云", "小雨", "大雨", "雷雨", "小雪"]
-
- result = []
- today = datetime.now()
-
- for i in range(data.days):
- date = today + timedelta(days=i)
- result.append(WeatherInfo(
- date=date.strftime("%Y-%m-%d"),
- temperature=round(random.uniform(15, 30), 1),
- condition=random.choice(weather_conditions),
- humidity=random.randint(30, 90)
- ))
-
- return result
- if __name__ == "__main__":
- import uvicorn
- uvicorn.run(app, host="0.0.0.0", port=8001)
- # 示例3:文件操作服务器
- from fastmcp import MCPServer, Request
- from fastapi import FastAPI
- from pydantic import BaseModel
- import os
- import json
- app = FastAPI()
- mcp_server = MCPServer(app)
- # 模拟文件系统(实际应用中使用真实文件系统)
- file_system = {}
- class FileWriteRequest(BaseModel):
- filename: str
- content: str
- class FileReadRequest(BaseModel):
- filename: str
- class FileListRequest(BaseModel):
- directory: str = "/"
- class FileDeleteRequest(BaseModel):
- filename: str
- @mcp_server.mcp_endpoint
- async def write_file(request: Request[FileWriteRequest]) -> bool:
- """将内容写入文件"""
- data = request.params
- file_system[data.filename] = data.content
- return True
- @mcp_server.mcp_endpoint
- async def read_file(request: Request[FileReadRequest]) -> str:
- """读取文件内容"""
- data = request.params
- if data.filename not in file_system:
- raise ValueError(f"文件 {data.filename} 不存在")
- return file_system[data.filename]
- @mcp_server.mcp_endpoint
- async def list_files(request: Request[FileListRequest]) -> list[str]:
- """列出指定目录中的文件"""
- return list(file_system.keys())
- @mcp_server.mcp_endpoint
- async def delete_file(request: Request[FileDeleteRequest]) -> bool:
- """删除文件"""
- data = request.params
- if data.filename not in file_system:
- raise ValueError(f"文件 {data.filename} 不存在")
- del file_system[data.filename]
- return True
- if __name__ == "__main__":
- import uvicorn
- uvicorn.run(app, host="0.0.0.0", port=8002)
- # 示例4:综合应用 - 个人助手服务
- from fastmcp import MCPServer, Request
- from fastapi import FastAPI
- from pydantic import BaseModel
- from datetime import datetime
- import json
- import random
- app = FastAPI()
- mcp_server = MCPServer(app)
- # 模拟数据存储
- notes_db = []
- todos_db = []
- contacts_db = []
- class Note(BaseModel):
- id: int = None
- title: str
- content: str
- created_at: str = None
- class Todo(BaseModel):
- id: int = None
- task: str
- completed: bool = False
- due_date: str = None
- class Contact(BaseModel):
- id: int = None
- name: str
- phone: str
- email: str = None
- class SearchRequest(BaseModel):
- query: str
- @mcp_server.mcp_endpoint
- async def add_note(request: Request[Note]) -> Note:
- """添加一条笔记"""
- note = request.params
- note.id = len(notes_db) + 1
- note.created_at = datetime.now().isoformat()
- notes_db.append(note)
- return note
- @mcp_server.mcp_endpoint
- async def get_notes(request: Request) -> list[Note]:
- """获取所有笔记"""
- return notes_db
- @mcp_server.mcp_endpoint
- async def add_todo(request: Request[Todo]) -> Todo:
- """添加一个待办事项"""
- todo = request.params
- todo.id = len(todos_db) + 1
- if not todo.due_date:
- todo.due_date = (datetime.now() + timedelta(days=1)).isoformat()
- todos_db.append(todo)
- return todo
- @mcp_server.mcp_endpoint
- async def get_todos(request: Request) -> list[Todo]:
- """获取所有待办事项"""
- return todos_db
- @mcp_server.mcp_endpoint
- async def complete_todo(request: Request[int]) -> Todo:
- """标记待办事项为已完成"""
- todo_id = request.params
- for todo in todos_db:
- if todo.id == todo_id:
- todo.completed = True
- return todo
- raise ValueError(f"待办事项 #{todo_id} 不存在")
- @mcp_server.mcp_endpoint
- async def add_contact(request: Request[Contact]) -> Contact:
- """添加联系人"""
- contact = request.params
- contact.id = len(contacts_db) + 1
- contacts_db.append(contact)
- return contact
- @mcp_server.mcp_endpoint
- async def get_contacts(request: Request) -> list[Contact]:
- """获取所有联系人"""
- return contacts_db
- @mcp_server.mcp_endpoint
- async def search(request: Request[SearchRequest]) -> dict:
- """搜索笔记、待办事项和联系人"""
- query = request.params.query.lower()
-
- matching_notes = [note for note in notes_db if query in note.title.lower() or query in note.content.lower()]
- matching_todos = [todo for todo in todos_db if query in todo.task.lower()]
- matching_contacts = [contact for contact in contacts_db if query in contact.name.lower()]
-
- return {
- "notes": matching_notes,
- "todos": matching_todos,
- "contacts": matching_contacts
- }
- if __name__ == "__main__":
- import uvicorn
- uvicorn.run(app, host="0.0.0.0", port=8003)
复制代码 小白指南:逐步明白
1. 什么是MCP?
想象你的AI助手(如ChatGPT)是一个智慧的专家,但被关在一个房间里,只能通过纸条与外界互换。MCP就像是给这个专家配备了一部电话,让它能打电话给各种服务:查天气、计算数学标题、管理你的日程等。
2. FastMCP和FastAPI的脚色
- FastAPI:提供电话线路和基础办法
- FastMCP:界说通话协议,确保AI能准确拨号和明白复兴
3. 搭建MCP服务器的步骤
- 安装须要的库:
- pip install fastmcp fastapi uvicorn
复制代码 - 创建服务器框架:
- from fastmcp import MCPServer
- from fastapi import FastAPI
- app = FastAPI()
- mcp_server = MCPServer(app)
复制代码 - 界说数据模子(哀求和相应的结构)
- 建立功能端点(用@mcp_server.mcp_endpoint装饰器)
- 启动服务器:
- import uvicorn
- uvicorn.run(app, host="0.0.0.0", port=8000)
复制代码 现实应用场景
- 数据分析助手:毗连数据处置惩罚工具
- 客户服务呆板人:访问CRM体系和知识库
- 智能文档助手:处置惩罚和天生各类文档
- 个人生产力工具:管理日程、条记和待服务项
最佳实践
- 明白界说数据模子:利用Pydantic确保输入输出格式准确
- 添加具体文档:每个端点都应有清楚的形貌
- 实现错误处置惩罚:优雅处置惩罚异常环境
- 利用异步功能:充分利用FastAPI的异步特性
- 添加验证和安全步调:掩护服务器不受恶意哀求攻击
结语
FastMCP和FastAPI的联合为AI模子提供了强大的扩展能力。通过本文先容的示例,纵然是编程新手也能构建自己的MCP服务器,让AI助手拥有更多实勤劳能。随着MCP生态体系的发展,我们可以等候更多创新应用的出现。
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。 |