429 lines
14 KiB
Markdown
429 lines
14 KiB
Markdown
# 多 Agent 平台 — 全栈开发子 Agent
|
||
|
||
基于 Google ADK (Agent Development Kit) 构建的多模型全栈开发 Agent 平台,内置三个独立 Agent,通过 REST API / MCP / CLI 多种方式调用,支持文件操作、终端命令、会话持久化、上下文压缩、长期记忆。
|
||
|
||
## 架构总览
|
||
|
||
```
|
||
用户 / CodeBuddy(主控)
|
||
│
|
||
├─ MCP ──► my_agent_server.py ──┐
|
||
├─ MCP ──► luna_server.py ──────┤
|
||
└─ MCP ──► qwen_server.py ──────┤
|
||
│
|
||
┌────────────────┘
|
||
▼
|
||
各自独立的 API Server(不同端口)
|
||
│
|
||
▼
|
||
App(dev_app)
|
||
│ events_compaction_config(LLM 摘要压缩)
|
||
▼
|
||
LlmAgent(root_agent)
|
||
│
|
||
┌──────────┼──────────┐
|
||
▼ ▼ ▼
|
||
文件系统 终端命令 记忆系统
|
||
MCP run_command preload_memory
|
||
```
|
||
|
||
## 三个 Agent
|
||
|
||
| Agent 名称 | 目录 | 模型 | API 端口 | 会话数据库 | MCP 服务器名 |
|
||
|-----------|------|------|---------|-----------|-------------|
|
||
| `my_agent` | `agents/my_agent/` | aq-first-combo | 8001 | `sessions_my.db` | `my-agent` |
|
||
| `luna_agent` | `agents/luna/` | gpt-5.6-luna | 8002 | `sessions_luna.db` | `luna-agent` |
|
||
| `qwen_agent` | `agents/qwen/` | astron-code-latest | 8003 | `sessions_qwen.db` | `qwen-agent` |
|
||
|
||
每个 Agent 完全独立:独立的模型配置、独立的 API Server、独立的会话数据库、独立的 MCP 入口。
|
||
|
||
## 核心能力
|
||
|
||
| 能力 | 说明 |
|
||
|------|------|
|
||
| **文件系统操作** | 读/写/列目录/搜索等 14 个工具(MCP: server-filesystem) |
|
||
| **终端命令执行** | 异步 subprocess,支持编译/构建/测试 |
|
||
| **网络搜索** | Tavily 搜索 + Fetch 抓取(默认关闭,见下文说明) |
|
||
| **SQLite 会话持久化** | 重启不丢,每个 Agent 独立数据库 |
|
||
| **上下文自动压缩** | 每 20 轮 LLM 摘要,长对话不爆 context window |
|
||
| **长期记忆框架** | InMemory + 自动存取,可扩展为向量库 |
|
||
| **REST API** | `/run`、`/run_sse`、会话管理、Swagger UI |
|
||
| **MCP 接口** | 可直接接入 CodeBuddy / Cursor / Windsurf |
|
||
| **A2A 协议** | Agent-to-Agent 标准协议(备用方案) |
|
||
|
||
## 快速开始
|
||
|
||
### 1. 环境准备
|
||
|
||
```bash
|
||
# 进入项目目录
|
||
cd d:/nzy/workspace_python/agent
|
||
|
||
# 创建虚拟环境(已创建可跳过)
|
||
python -m venv .venv
|
||
|
||
# 激活虚拟环境
|
||
.venv\Scripts\activate # Windows
|
||
# source .venv/bin/activate # Linux/Mac
|
||
|
||
# 安装依赖
|
||
pip install -r requirements.txt
|
||
```
|
||
|
||
### 2. 配置环境变量
|
||
|
||
每个 Agent 有独立的 `.env` 文件,在对应 agent 目录下:
|
||
|
||
```
|
||
agents/my_agent/.env # my_agent 配置
|
||
agents/luna/.env # luna_agent 配置
|
||
agents/qwen/.env # qwen_agent 配置
|
||
```
|
||
|
||
主要配置项(详见下方"配置说明"):
|
||
- `VLLM_API_BASE` — vLLM API 端点
|
||
- `VLLM_MODEL` — 模型名称
|
||
- `VLLM_API_KEY` — API Key
|
||
- `AGENT_WORKSPACE_DIR` — Agent 可访问的工作目录
|
||
|
||
### 3. 启动 API Server
|
||
|
||
每个 Agent 有独立的 API Server,在对应 agent 目录下启动:
|
||
|
||
```bash
|
||
# 启动 my_agent(端口 8001)
|
||
cd agents/my_agent && python api_server.py
|
||
|
||
# 启动 luna_agent(端口 8002)
|
||
cd agents/luna && python api_server.py
|
||
|
||
# 启动 qwen_agent(端口 8003)
|
||
cd agents/qwen && python api_server.py
|
||
```
|
||
|
||
启动后访问:
|
||
- **Swagger UI**: http://127.0.0.1:8001/docs — 浏览器直接测试接口
|
||
- **列出 Agent**: http://127.0.0.1:8001/list-apps
|
||
|
||
### 4. 配置 MCP(CodeBuddy 调用)
|
||
|
||
全局配置文件路径:`~/.codebuddy/.mcp.json`
|
||
|
||
```json
|
||
{
|
||
"mcpServers": {
|
||
"my-agent": {
|
||
"type": "stdio",
|
||
"command": "D:\\nzy\\workspace_python\\agent\\.venv\\Scripts\\python.exe",
|
||
"args": ["d:\\nzy\\workspace_python\\agent\\mcp_dev_agent\\my_agent_server.py"],
|
||
"description": "My Agent (aq-first-combo) 全栈开发助手"
|
||
},
|
||
"luna-agent": {
|
||
"type": "stdio",
|
||
"command": "D:\\nzy\\workspace_python\\agent\\.venv\\Scripts\\python.exe",
|
||
"args": ["d:\\nzy\\workspace_python\\agent\\mcp_dev_agent\\luna_server.py"],
|
||
"description": "Luna Agent (gpt-5.6-luna) 全栈开发助手"
|
||
},
|
||
"qwen-agent": {
|
||
"type": "stdio",
|
||
"command": "D:\\nzy\\workspace_python\\agent\\.venv\\Scripts\\python.exe",
|
||
"args": ["d:\\nzy\\workspace_python\\agent\\mcp_dev_agent\\qwen_server.py"],
|
||
"description": "Qwen Agent (astron-code-latest) 全栈开发助手"
|
||
}
|
||
}
|
||
}
|
||
```
|
||
|
||
> **注意**:Windows 路径使用反斜杠 `\\`。MCP Server 通过 venv 的 python.exe 直接启动,不需要手动激活虚拟环境。
|
||
|
||
重启 CodeBuddy 后,三个 MCP 服务器会自动连接,每个提供一个 `run_dev_agent` 工具。
|
||
|
||
## 使用方式
|
||
|
||
### 方式一:CLI 对话(每个 Agent 独立)
|
||
|
||
```bash
|
||
# my_agent 对话
|
||
cd agents/my_agent && python chat.py
|
||
|
||
# luna_agent 对话
|
||
cd agents/luna && python chat.py
|
||
|
||
# qwen_agent 对话
|
||
cd agents/qwen && python chat.py
|
||
|
||
# 指定 session_id 继续对话
|
||
python chat.py --session my_session
|
||
|
||
# 列出所有会话
|
||
python chat.py --list
|
||
|
||
# 删除会话
|
||
python chat.py --delete my_session
|
||
```
|
||
|
||
### 方式二:Swagger UI
|
||
|
||
打开对应端口的 `/docs`,在浏览器里直接测试接口。
|
||
|
||
**常用接口**:
|
||
- `POST /run` — 同步运行 agent,返回完整事件列表
|
||
- `POST /run_sse` — SSE 流式运行
|
||
- `GET /apps/{app}/users/{user}/sessions/{id}` — 获取会话
|
||
- `POST /apps/{app}/users/{user}/sessions/{id}` — 创建会话
|
||
|
||
### 方式三:MCP 工具(CodeBuddy / Cursor)
|
||
|
||
配置好 MCP 后,直接让 IDE 中的 AI 调用对应 Agent 的 `run_dev_agent` 工具。
|
||
|
||
**工具参数**:
|
||
|
||
| 参数 | 必填 | 说明 |
|
||
|------|------|------|
|
||
| `task` | ✅ | 任务描述,越详细越好 |
|
||
| `session_id` | ❌ | 会话 ID,不传则为 `default`。用于多轮续聊 |
|
||
|
||
### 方式四:curl 直接调用
|
||
|
||
```bash
|
||
curl -X POST http://127.0.0.1:8001/run \
|
||
-H "Content-Type: application/json" \
|
||
-d '{
|
||
"appName": "my_agent",
|
||
"userId": "test_user",
|
||
"sessionId": "test_001",
|
||
"newMessage": {
|
||
"role": "user",
|
||
"parts": [{"text": "你好,请介绍一下你自己"}]
|
||
}
|
||
}'
|
||
```
|
||
|
||
## 项目结构
|
||
|
||
```
|
||
agent/
|
||
├── api_server.py # 旧版根目录 API Server(my_agent,保留兼容)
|
||
├── chat.py # 旧版根目录 CLI(my_agent,保留兼容)
|
||
├── a2a_server.py # A2A Server(备用)
|
||
├── a2a_client.py # A2A 客户端测试
|
||
├── test_sse_client.py # SSE 测试
|
||
├── requirements.txt # Python 依赖
|
||
│
|
||
├── agents/ # 所有 Agent 目录
|
||
│ ├── __init__.py
|
||
│ │
|
||
│ ├── my_agent/ # My Agent (aq-first-combo)
|
||
│ │ ├── __init__.py
|
||
│ │ ├── agent.py # Agent 定义(人设、工具、instruction)
|
||
│ │ ├── app.py # App 容器(上下文压缩配置)
|
||
│ │ ├── api_server.py # 独立 API Server(端口 8001)
|
||
│ │ ├── chat.py # 独立 CLI 对话工具
|
||
│ │ ├── .env # 环境变量配置
|
||
│ │ └── .adk/ # ADK 会话数据
|
||
│ │
|
||
│ ├── luna/ # Luna Agent (gpt-5.6-luna)
|
||
│ │ ├── __init__.py
|
||
│ │ ├── agent.py
|
||
│ │ ├── app.py
|
||
│ │ ├── api_server.py # 独立 API Server(端口 8002)
|
||
│ │ ├── chat.py # 独立 CLI 对话工具
|
||
│ │ └── .env
|
||
│ │
|
||
│ └── qwen/ # Qwen Agent (astron-code-latest)
|
||
│ ├── __init__.py
|
||
│ ├── agent.py
|
||
│ ├── app.py
|
||
│ ├── api_server.py # 独立 API Server(端口 8003)
|
||
│ ├── chat.py # 独立 CLI 对话工具
|
||
│ └── .env
|
||
│
|
||
├── mcp_dev_agent/ # MCP Server(CodeBuddy 入口)
|
||
│ ├── server.py # 通用 MCP Server 逻辑(FastMCP)
|
||
│ ├── my_agent_server.py # my_agent MCP 入口(端口 8001)
|
||
│ ├── luna_server.py # luna_agent MCP 入口(端口 8002)
|
||
│ └── qwen_server.py # qwen_agent MCP 入口(端口 8003)
|
||
│
|
||
├── mcp_server/ # 旧版任务队列 MCP Server(保留参考)
|
||
│ └── ...
|
||
│
|
||
├── mcp_tools/ # 备用 MCP 工具(保留参考)
|
||
│ └── command_executor/
|
||
│
|
||
├── data/ # 数据目录(运行时生成)
|
||
│ ├── sessions_my.db # my_agent 会话数据库
|
||
│ ├── sessions_luna.db # luna_agent 会话数据库
|
||
│ └── sessions_qwen.db # qwen_agent 会话数据库
|
||
│
|
||
└── PLAN.md # 项目计划文档
|
||
```
|
||
|
||
## 配置说明
|
||
|
||
### 环境变量(Agent .env)
|
||
|
||
每个 Agent 目录下的 `.env` 文件:
|
||
|
||
```env
|
||
# vLLM API 配置
|
||
VLLM_API_BASE=https://9router.aqroid.cn/v1 # vLLM 端点地址
|
||
VLLM_MODEL=aq-first-combo # 模型名
|
||
VLLM_API_KEY=sk-... # API Key
|
||
|
||
# Agent 工作目录(文件系统 MCP 根目录)
|
||
AGENT_WORKSPACE_DIR=D:\nzy\workspace_git
|
||
|
||
# Tavily 搜索 API Key(启用搜索工具时需要)
|
||
TAVILY_API_KEY=tvly-dev-...
|
||
|
||
# Windows 编码
|
||
PYTHONUTF8=1
|
||
```
|
||
|
||
### API Server 配置
|
||
|
||
通过环境变量或直接修改对应 `api_server.py`:
|
||
|
||
| 变量 | 默认值 | 说明 |
|
||
|------|--------|------|
|
||
| `API_SERVER_HOST` | `0.0.0.0` | 监听地址 |
|
||
| `API_SERVER_PORT` | `8001/8002/8003` | 监听端口(各 Agent 不同) |
|
||
|
||
### MCP Server 配置
|
||
|
||
每个 `*_server.py` 入口脚本顶部硬编码了对应的 API 地址和 Agent 名称:
|
||
|
||
| Agent | API URL | App Name |
|
||
|-------|---------|----------|
|
||
| my_agent | `http://127.0.0.1:8001` | `my_agent` |
|
||
| luna_agent | `http://127.0.0.1:8002` | `luna_agent` |
|
||
| qwen_agent | `http://127.0.0.1:8003` | `qwen_agent` |
|
||
|
||
## 会话与记忆
|
||
|
||
### 会话持久化
|
||
|
||
每个 Agent 的会话存储在独立的 SQLite 数据库中(`data/sessions_*.db`),重启服务不丢失。
|
||
|
||
- **同入口续聊**:同一个 session_id 下次接着聊
|
||
- **跨入口共享**:同一个 Agent 的 API Server、CLI、MCP 共用同一个数据库
|
||
|
||
### 上下文压缩
|
||
|
||
长对话会自动摘要压缩(默认每 20 轮),防止 context window 溢出:
|
||
|
||
- 滑动窗口压缩 + 重叠摘要(保持连续性)
|
||
- Token 超阈值紧急压缩(默认 50k)
|
||
- 原始事件完整保留(可回溯)
|
||
|
||
配置在各 Agent 的 `app.py` 的 `EventsCompactionConfig`。
|
||
|
||
### 长期记忆
|
||
|
||
当前使用 `InMemoryMemoryService`(内存版),特性:
|
||
|
||
- 每轮对话结束自动保存(`after_agent_callback`)
|
||
- 每轮对话开始自动加载相关记忆(`preload_memory`)
|
||
- 进程重启后记忆丢失
|
||
|
||
**后续可扩展**:替换为 `ChromaMemoryService` 等向量数据库,实现持久化语义搜索。
|
||
|
||
## 工具说明
|
||
|
||
### 文件系统工具(14 个)
|
||
|
||
read_file、read_text_file、read_media_file、read_multiple_files、write_file、edit_file、create_directory、list_directory、list_directory_with_sizes、directory_tree、move_file、search_files、get_file_info、list_allowed_directories
|
||
|
||
### 终端命令
|
||
|
||
- **run_command** — 执行终端命令,支持自定义工作目录和超时
|
||
|
||
### 记忆工具
|
||
|
||
- **preload_memory** — 每轮自动检索并注入相关历史记忆(系统自动调用,不占工具回合)
|
||
|
||
### 网络搜索工具(默认关闭)
|
||
|
||
Tavily 搜索 + Fetch 抓取默认注释掉了,因为大响应内容可能导致请求体过大。如需启用:
|
||
|
||
1. 取消对应 `agent.py` 中 `fetch_mcp` 和 `tavily_mcp` 的注释
|
||
2. 配置 `TAVILY_API_KEY` 环境变量
|
||
|
||
## 工作流程
|
||
|
||
标准工作流程:
|
||
|
||
1. 理解任务需求和项目上下文
|
||
2. 使用文件系统工具浏览项目结构、读取相关文件
|
||
3. 编写或修改代码
|
||
4. 使用 run_command 运行编译/构建/测试
|
||
5. 验证结果后,结构化报告完成情况
|
||
|
||
**报告格式**:
|
||
- 状态:成功 / 部分完成 / 失败(需上报)
|
||
- 修改的文件:列出所有修改的文件路径
|
||
- 变更摘要:简述做了什么
|
||
- 验证结果:编译/测试是否通过
|
||
- 需要主控关注:如有问题,详细说明
|
||
|
||
## 部署说明
|
||
|
||
### 本地开发
|
||
|
||
```bash
|
||
# 终端 1:启动 my_agent API Server
|
||
cd agents/my_agent && python api_server.py
|
||
|
||
# 终端 2(可选):用 CLI 测试
|
||
cd agents/my_agent && python chat.py
|
||
|
||
# 或者直接用 Swagger UI:http://127.0.0.1:8001/docs
|
||
```
|
||
|
||
### 上云准备
|
||
|
||
- API Server 是标准 FastAPI 应用,可直接部署到任何支持 Python 的平台
|
||
- SQLite 会话数据库需换成数据库服务(PostgreSQL / MySQL)
|
||
- MemoryService 需换成托管向量数据库(Chroma / Pinecone / Vertex AI)
|
||
- 文件系统 MCP 需接入云存储或挂载盘
|
||
|
||
## 技术栈
|
||
|
||
| 组件 | 技术 | 版本 |
|
||
|------|------|------|
|
||
| Agent 框架 | Google ADK | 2.5.0 |
|
||
| LLM 接入 | LiteLLM + vLLM (OpenAI 兼容) | 1.80.0 |
|
||
| MCP | FastMCP (Model Context Protocol SDK) | 1.29.0 |
|
||
| HTTP 服务 | FastAPI + Uvicorn | - |
|
||
| 会话存储 | SQLite | - |
|
||
| A2A 协议 | a2a-sdk | 1.1.2 |
|
||
|
||
## 常见问题
|
||
|
||
### Q: MCP 服务器连不上?
|
||
|
||
A: 请检查:
|
||
1. 对应 Agent 的 API Server 是否已启动(`agents/my_agent/api_server.py` 等)
|
||
2. `.mcp.json` 中的 python.exe 路径和脚本路径是否正确(Windows 使用反斜杠)
|
||
3. 端口是否被占用(`netstat -ano | findstr 8001`)
|
||
|
||
### Q: 调用时报 413 Request Entity Too Large?
|
||
|
||
A: vLLM 端点的 nginx 限制了请求体大小。当前已暂时关闭 Tavily 和 Fetch 工具以减小请求体。如需要启用,需联系端点管理员调大限制。
|
||
|
||
### Q: 会话数据存在哪?
|
||
|
||
A: `data/sessions_*.db`,每个 Agent 有独立的 SQLite 数据库文件。
|
||
|
||
### Q: 怎么重置会话?
|
||
|
||
A: 用 CLI 的 `python chat.py --delete <session_id>`,或直接调用 DELETE 会话 API,或直接删除对应的 `.db` 文件。
|
||
|
||
### Q: 三个 Agent 有什么区别?
|
||
|
||
A: 区别只在使用的模型不同(aq-first-combo / gpt-5.6-luna / astron-code-latest),工具集和能力完全一致。可以根据任务特点选择合适的模型。
|
||
|
||
## 许可证
|
||
|
||
MIT
|