MCP 客户端聊天(FastAPI + Streamlit)
概述
这个项目是一个简洁但功能完备的MCP(模型上下文协议)客户端,具备以下特性:
- 后端:一个FastAPI服务,通过标准输入输出(stdio)连接到MCP服务器,提供简单的REST端点,并使用大型语言模型(默认为LM Studio)来协调聊天流程。它可以在每次查询时检查和调用MCP工具。
- 前端:使用Streamlit构建的聊天用户界面,与后端进行交互,维护聊天历史记录,展示可用的MCP工具,并为助手的回复添加动画效果。
流程:
- 用户通过Streamlit聊天界面发送了一个查询。
- FastAPI 后端将对话转发给一个带有系统消息的大型语言模型(LM Studio),该系统消息列出了可用的 MCP 工具。
- 如果大型语言模型(LLM)以函数调用风格的JSON形式响应,指明了要调用的工具,后端将调用该MCP工具一次,并将结果附加到对话中。
- 后端再次向大型语言模型(LLM)查询以获取最终答案,然后将完整的消息历史返回给前端进行渲染。
技术栈
- FastAPI用于后端API
- 用于stdio连接和工具调用的MCP Python客户端
- 用于聊天完成的LM Studio(本地版)
- 用于聊天式前端的Streamlit
- 用于环境和依赖管理的UV(或“UV用于环境与依赖管理”)
______________________________________________________________________
先决条件
- Python 3.10及以上版本
- 已安装UV(参见
https://docs.astral.sh/uv/) - 在本地运行的LM Studio(或兼容OpenAI风格的服务器)
http://localhost:1234带有模型qwen/qwen3-8b(可配置为api/mcp_client.py) - 一个可通过stdio访问并配置在
api/main.py -> Settings.server_command并且Settings.server_args
______________________________________________________________________
设置
除非另有说明,否则请在项目根目录下运行这些命令。
- 使用uv创建并激活一个虚拟环境:
uv venv- 同步依赖项:
uv sync- (可选)验证安装:
uv run python -V
uv run pip list | cat______________________________________________________________________
运行后端(FastAPI)
从项目根目录进入 api 创建文件夹并使用 Uvicorn 启动服务器:
cd api
uv run uvicorn main:app --host 0.0.0.0 --port 8000注:
- 启动时,该应用程序使用(某种方式)连接到您的MCP服务器
Settings.server_command并且Settings.server_args在api/main.py调整这些设置以匹配您的MCP服务器。 - 出于本地开发的便利性,CORS 默认开启。
API终端点
GET /tools返回从服务器检测到的MCP工具列表(包括名称、描述、输入模式)。POST /query(衣服等)带身体(部分的)/(衣服等)有主体{ "query": "..." }执行上述描述的聊天协调流程,并返回完整的消息历史记录列表。
示例请求:
curl -X POST http://localhost:8000/query \
-H "Content-Type: application/json" \
-d '{"query":"List available tools and use one if relevant."}' | cat______________________________________________________________________
运行前端(Streamlit)
在项目根目录之外的另一个终端中,启动 Streamlit:
uv run streamlit run frontend/app.py该应用程序将:
- 从(指定位置)加载可用工具
GET /tools并将它们显示在侧边栏中。 - 提供一个聊天界面,用于向(助手)发送提示
POST /query并显示基于角色的消息。 - 为助手回复显示一个简单的打字动画。
确保后端正在运行 http://localhost:8000 默认设置。您可以更改API基础地址 frontend/app.py 如需使用。
______________________________________________________________________
配置
- 后端大型语言模型(LLM)设置:
api/mcp_client.py
- self.lmstudio_url默认 http://localhost:1234/v1/chat/completions - self.lmstudio_model默认 qwen/qwen3-8b
- MCP服务器设置:
api/main.py
- Settings.server_command默认 "uv" - Settings.server_args默认目录和 run main.py 对于示例服务器;请更新为您的MCP服务器命令和参数。
如上所示,配置直接在代码文件中处理。
______________________________________________________________________
它是如何工作的(详细说明)
- FastAPI使用一个生命周期上下文来初始化一个长生命周期的对象
MCPClient该系统管理MCP会话并跟踪完整的对话状态。 MCPClient.process_query()附加用户消息并调用一次大型语言模型(LLM)。LLM收到一个系统指令,该指令列出了可用的MCP工具,并要求它在适当的时候调用工具时返回JSON。- 如果响应能被解析为包含JSON格式的数据,且
tool在该领域,客户端恰好调用一次该MCP工具,并将其实现的结果捕获为对话中的一个系统工具结果(tool_result)。 - 客户端再次调用大型语言模型(LLM),利用工具输出生成最终的助手回复。
- 完整的对话被返回到前端,并同时以JSON文件的形式记录在
api/conversations/以便追溯。
设计选择:
- 每个查询恰好调用一次工具,以保持流程的可预测性。
- LM输出已进行清理以去除 `` 痕迹并使内容规范化。
- 消息被序列化为OpenAI风格
[{role, content: [{type: "text", text: "..."}]}]在发送给LM Studio之前。
______________________________________________________________________
故障排除
- 后端无法连接到MCP服务器
- 检查 Settings.server_command 并且 Settings.server_args 在 api/main.py。 - 尝试使用相同的命令手动运行您的MCP服务器,以确认其能否启动。
- LM Studio 错误(非200状态码)
- 确保LM Studio服务器正在运行 http://localhost:1234。 - 确认模型名称 api/mcp_client.py 已可用。
- 来自Streamlit的CORS或连接错误
- 确保FastAPI后端可通过以下地址访问: http://localhost:8000。 - 在某些系统上,防火墙或VPN可能会阻止本地主机端口。
- 侧边栏未显示任何工具
- 验证您的MCP服务器是否确实提供了工具。 - 检查后端日志 mcp_client.log 对于任何错误。
______________________________________________________________________
项目结构
api/
main.py # FastAPI app, lifespan connects to MCP server
mcp_client.py # MCPClient: LLM calls, tool invocation, logging
conversations/ # JSON logs of each conversation
utils/logger.py # Unified file+console logging
frontend/
app.py # Streamlit chat UI
pyproject.toml # Dependencies managed by uv
uv.lock # Resolved lockfile______________________________________________________________________
许可证
麻省理工学院(MIT)许可证(或您偏好的许可证)
