搭建MCP服务:写一个最简易的MCP服务了解其运行流程
大家在用AI助手的时候肯定遇到过这种情况:想让ChatGPT查天气、查快递、查本地文件,它却答不上来——不是模型不够聪明,而是它碰不到外部世界的数据,就像人被关在房间里,没法出门查信息。传统想让AI调用外部工具,要么写一堆适配代码,要么每个工具单独对接,又乱又麻烦。
这时候MCP就派上用场了,它不是什么高深的底层协议,更像是AI和外部工具的万能转接器。不管是天气接口、数据库、本地脚本,还是第三方平台,只要接上MCP,AI就能像点外卖一样,轻松调用这些工具,不用管底层怎么通信。简单说,MCP解决的就是“AI如何安全、规范、省心地调用外部能力”这个痛点,让AI从“只会聊天”变成“能办事的助手”。
本文将从零到一,带你搭建一个基于高德地图API的天气查询MCP服务,手把手完成MCP服务开发、Cursor编辑器集成、LangChain Agent调用全流程落地,全程代码可直接复用,兼顾理论深度与实操性,新手也能轻松上手。
一、先搞懂:MCP到底是什么?
两个日常场景:
- 场景1:你让Cursor编辑器“帮我查北京天气并写到代码注释里”,编辑器自带的AI本身查不了天气,但是通过MCP,它能一键调用我们写的天气工具,拿到结果直接回填,全程不用你手动调接口。
- 场景2:你做了个智能问答Agent,想让它既能聊天又能查快递、查天气,不用给每个接口写适配代码,把这些能力打包成MCP工具,Agent就能自动识别调用,改工具、加工具都不用动Agent核心代码。
说白了,MCP就是一套通用的“工具调用协议” :AI按这个规矩发请求,工具按这个规矩返回结果,双方各司其职,再也不用点对点适配。它的核心就是解耦,让AI专心做决策,工具专心做执行。
MCP的核心优势
- 标准化通信:统一工具调用格式,无需针对每个模型单独适配接口
- 低耦合易扩展:工具逻辑与模型调用分离,新增、修改工具不影响主流程
- 跨平台兼容:支持Stdio、WebSocket等多种传输方式,适配编辑器、Agent框架等多种场景
- 轻量级无侵入:无需复杂部署,本地脚本即可启动MCP服务,开发成本极低
对比一下就更清楚:没有MCP的时候,想让AI调用高德天气,得写接口调用、参数解析、异常捕获,再把逻辑嵌进AI代码里,后期想换百度天气,就得改一大段代码;有了MCP之后,把天气查询单独做成一个工具模块,AI只需要通过MCP喊一句“查北京天气”,工具就返回结果,后期换接口、加功能,只改工具本身,AI代码完全不用动。
这次我们用FastMCP框架开发,就是看中它足够轻量化,几行代码就能把普通Python函数,变成AI能调用的MCP工具,对小白极其友好,不用学复杂的协议细节,会写Python函数就能上手。
二、环境准备:前置依赖安装
开始开发前,先搭建Python虚拟环境并安装核心依赖包,避免版本冲突:
# 创建虚拟环境(可选,推荐)
python3 -m venv mcp-env
# 激活环境(macOS/Linux)
source mcp-env/bin/activate
# Windows激活
# mcp-env\Scripts\activate
# 安装核心依赖
pip3 install requests fastmcp pydantic langchain langchain-openai langchain-mcp-adapters langgraph
同时需要提前准备高德地图开放平台API Key:前往高德开放平台注册账号,创建应用后获取Web服务类型的Key,用于后续天气接口调用。
三、核心实战:开发天气查询MCP服务
我们就拿查天气这个最刚需的场景练手,这个例子足够典型:平时AI没法直接联网查天气,我们把高德天气API封装成MCP工具后,不管是Cursor里的AI,还是自己搭的LangChain Agent,都能随时调用这个能力。后续想做查快递、查股价、读本地文件,都是一模一样的思路,换个接口逻辑就行。
3.1 编写MCP服务代码
新建 shell_tools.py 文件,这是我们的MCP服务核心文件,通过FastMCP注册天气查询工具,实现高德地图API的封装与标准化输出:
import requests
from typing import Annotated
from mcp.server.fastmcp import FastMCP
from pydantic import Field
# 初始化FastMCP实例
mcp = FastMCP()
# 注册MCP工具:定义工具名称、描述、入参规则
@mcp.tool(name="city_weather", description="查询指定城市的实时天气状况,支持国内大部分地级市")
def get_weather(city: Annotated[str, Field(description="目标城市名称(中文全称)", examples=["北京", "上海", "广州", "深圳"])]) -> str:
"""
封装高德地图天气查询API,标准化返回天气数据
接口文档:https://lbs.amap.com/api/webservice/api/weather/weather-info
"""
# 替换为自己的高德地图API Key
AMAP_KEY = "your_amap_api_key"
# 高德天气基础查询接口
url = f"https://restapi.amap.com/v3/weather/weatherInfo?city={city}&key={AMAP_KEY}&extensions=base"
try:
# 发送请求,设置超时避免阻塞
resp = requests.get(url, timeout=10)
resp.raise_for_status()
data = resp.json()
# 校验接口返回状态
if data.get("status") != "1" or not data.get("lives"):
return f"❌ 查询{city}天气失败:接口返回异常或城市不支持"
# 解析实时天气数据
live_data = data["lives"][0]
# 格式化返回结果,提升可读性
return (
f"🌤️ {live_data['city']} 实时天气\n"
f"🌡️ 当前温度:{live_data['temperature']}℃\n"
f"☁️ 天气状况:{live_data['weather']}\n"
f"💨 风向风力:{live_data['winddirection']}风 {live_data['windpower']}级\n"
f"💧 空气湿度:{live_data['humidity']}%"
)
except requests.exceptions.Timeout:
return "❌ 查询天气超时:请检查网络或稍后重试"
except Exception as e:
return f"❌ 查询天气出错:{str(e)}"
if __name__ == "__main__":
# 启动MCP服务,采用stdio传输协议(最常用,适配编辑器、Agent)
mcp.run(transport="stdio")
3.2 代码核心要点解析
- 工具注册:通过
@mcp.tool装饰器定义工具名称、功能描述,大模型通过描述理解工具用途 - 参数校验:借助Pydantic的Field注解规范入参,明确参数含义和示例,降低模型调用出错率
- 异常处理:针对超时、接口异常、参数错误等场景做兜底处理,保证服务稳定性
- 传输协议:选用stdio标准输入输出,轻量级无需额外端口,适配绝大多数集成场景
启动测试:直接运行python shell_tools.py,若控制台无报错,说明MCP服务启动成功,等待客户端调用即可。
四、实战集成1:Cursor编辑器接入MCP
Cursor作为主打AI协作的编辑器,原生支持MCP协议,这就意味着:我们不用改Cursor的任何设置,只需要写一段配置,把本地的天气MCP工具“挂载”到Cursor上,编辑器里的AI就能直接用这个工具。
举个实际例子:以前你在Cursor里问“北京今天多少度”,AI只会说没法联网查询;现在接入MCP后,你发同样的问题,AI会自动调用我们写的city_weather工具,秒回温度、湿度、风力这些详细信息,甚至能帮你把天气数据插入到代码注释里,效率直接拉满。
4.1 配置MCP服务
- 打开Cursor编辑器,按下
Cmd + Shift + P(Windows:Ctrl + Shift + P),输入 MCP: Open Settings 打开配置文件 - 在
mcpServers节点下添加自定义MCP服务配置,替换为你的shell_tools.py绝对路径
{
"mcpServers": {
"my_mcp_shell": {
"type": "stdio",
"command": "python3",
"args": ["/Users/xxx/你的项目路径/shell_tools.py"]
}
}
}
4.2 验证调用
保存配置后,Cursor会自动加载MCP服务。在编辑器对话窗口直接输入:帮我查一下今天北京的天气,大模型会自动调用我们开发的 city_weather 工具,返回格式化的天气结果,无需额外配置,开箱即用。
避坑提示:Windows系统需将 command 改为 python,确保Python环境已加入系统环境变量;路径建议使用绝对路径,避免相对路径加载失败。
五、集成2:LangChain Agent调用MCP
如果说Cursor是AI编辑器,那LangChain就是搭建自定义AI Agent的框架,比如我们想做一个专属天气助理Agent,能听懂自然语言、自动判断要不要查天气、调用工具后整理结果,MCP就是Agent和天气工具之间的桥梁。
举个例子:用户问Agent“明天去北京要不要带伞”,Agent会先分析需求,知道需要查天气,然后通过MCP调用我们的工具,拿到天气和降水概率后,再给出“带伞/不用带伞”的结论,整个过程全自动,不用人工干预。
5.1 编写Agent调用代码
import asyncio
import os
import uuid
from langchain_core.messages import HumanMessage
from langchain_core.runnables import RunnableConfig
from langchain_mcp_adapters.sessions import StdioConnection
from langgraph.prebuilt import create_react_agent
from langchain_core.prompts import ChatPromptTemplate
from langchain_openai import ChatOpenAI
from langchain_mcp_adapters.client import MultiServerMCPClient
from pydantic import SecretStr
# 初始化大模型:适配主流大模型API,这里以Doubao为例
llm = ChatOpenAI(
base_url="https://api.302.ai/v1",
api_key=SecretStr(os.getenv("DASHSCOPE_API_KEY")), # 从环境变量读取密钥,更安全
model="Doubao-1.5-lite-32k",
timeout=None,
)
# 定义Agent系统提示词,明确角色定位
prompt = ChatPromptTemplate.from_messages([
("system", "你是专业的私人助理,可调用外部工具精准解答问题,回答简洁易懂、信息准确"),
("human", "{messages}"),
])
async def run_mcp_agent():
"""连接MCP服务,创建ReAct Agent并调用天气查询工具"""
async def get_mcp_tools():
# 配置MCP连接:Stdio方式对接本地MCP服务
mcp_config = {
"my_mcp": StdioConnection(
transport="stdio",
command="python3",
args=["/Users/xxx/你的项目路径/shell_tools.py"], # 替换为MCP文件绝对路径
encoding="utf-8",
)
}
# 初始化MCP客户端,加载工具
client = MultiServerMCPClient(mcp_config)
return await client.get_tools()
# 获取MCP工具列表
tools = await get_mcp_tools()
# 创建ReAct智能Agent
agent = create_react_agent(model=llm, prompt=prompt, tools=tools)
# 执行查询:自然语言指令
response = await agent.ainvoke(
input=HumanMessage(content="今天北京天气怎么样?"),
config=RunnableConfig(configurable={"session_id": str(uuid.uuid4())})
)
# 打印最终结果
print(response["messages"][-1].content)
if __name__ == '__main__':
# 运行异步Agent
asyncio.run(run_mcp_agent())
5.2 运行与调试
- 提前在环境变量中配置API密钥,避免硬编码泄露
- 确保MCP服务已启动(或直接运行Agent代码,会自动拉起MCP服务)
- 运行脚本,Agent会自动判断是否需要调用MCP工具,完成天气查询并返回结果
六、MCP开发与集成避坑总结
- API密钥安全:严禁硬编码密钥,建议通过环境变量、配置文件读取
- 路径问题:Cursor和LangChain集成时,务必使用绝对路径指向MCP脚本
- 传输协议:本地开发优先用stdio,远程服务可切换为websocket
- 工具描述规范:工具和参数描述要精准,大模型依赖描述理解工具用途,描述模糊易导致调用失败
- 异常兜底:完善异常处理,避免MCP服务崩溃影响主流程
七、写在最后
MCP作为大模型工具调用的标准化方案,正在成为AI Agent开发的基础设施,它彻底解决了工具集成的碎片化问题,让开发者专注于工具逻辑本身,而非适配工作。本文的天气查询MCP服务只是一个入门案例,你可以基于这套框架,快速开发数据库查询、文件操作、第三方API调用等各类MCP工具,轻松拓展大模型的能力边界。
社区和各大厂商中提供了大量的MCP服务可以给开发者直接调用,大大增强了AI的功能。