# LineUp Agents — 架构设计文档 **状态:** 讨论稿,持续更新 **最后更新:** 2026-07-25 --- ## 一、产品定位 LineUp Agents 是一个**远程 Agent 操作交互端**。用户通过手机或 Web App,与运行在本地或服务器上的 AI Agent 进行顺畅的交互。 不是任务管理系统。Agent 的任务拆解、执行、管理,属于 Agent 自己的工作范畴,不属于 LineUp 的职责。 --- ## 二、架构总览 ```text ┌─────────────────┐ ┌─────────────────────────┐ │ 用户 App 端 │ │ Agent 机器 │ │ (Web / 未来移动端)│ │ │ │ │ │ ┌─────────────────────┐ │ │ ┌─────────────┐ │ │ │ LineUp 插件 │ │ │ │ 工具渲染层 │ │ WebSocket │ │(嵌入 Agent 进程内) │ │ │ │ Confirm │ │◄────────►│ │ │ │ │ │ Input │ │ │ │ WebSocket 端口 │ │ │ │ SVG Renderer │ │ │ └─────────┬───────────┘ │ │ │ ... │ │ │ │ │ │ └─────────────┘ │ │ 进程内通信 │ │ │ │ │ │ │ ┌─────────────┐ │ │ ┌─────────▼───────────┐ │ │ │ 消息协议层 │ │ │ │ Agent 核心 │ │ │ │ WebSocket │ │ │ │ (Hermes / │ │ │ │ 连接管理 │ │ │ │ OpenClaw / 其他) │ │ │ └─────────────┘ │ │ └─────────────────────┘ │ └─────────────────┘ └─────────────────────────┘ ``` --- ## 三、已敲定的设计决策 ### 3.1 总体架构 | 决策 | 当期结论 | 后续扩展思路 | |------|---------|-------------| | 网络模式 | 局域网直连,App 直接连 Agent 插件暴露的 WebSocket 端口 | — | | 中转服务 | 不做中转 | 需要远程连接时引入中转服务 | | Agent 接入方式 | 每个 Agent 框架写一个插件,插件内开 WebSocket 端口 + 进程内通信 | — | | 端口配置 | 固定端口(默认 9527),支持环境变量覆盖 | — | | 发现方式 | 手动输入 IP:端口 | mDNS 广播自动发现 | | App 端技术方向 | 响应式 Web | 原生移动端 App | | 连接认证 | 预共享 Token,用户在插件配置中设定,App 连接时提供 | 端到端加密,密钥交换 | | 工具路由方式 | 字典路由,按工具名映射到对应的处理函数 | 可引入框架级路由 | ### 3.2 协议分层 三层结构,层间独立不耦合: ``` 第一层:通讯协议层 解决的问题:管道怎么通 包含:WebSocket 连接建立、身份标识交换、心跳保活、断线重连 第二层:消息协议层 解决的问题:消息长什么样子 包含:统一信封格式、消息路由、版本号、消息去重 第三层:工具协议层 解决的问题:App 能干什么 包含:工具发现(查询可用工具)、工具调用、返回结果 注:工具定义格式复用 MCP 的 JSON Schema 方式 ``` ### 3.3 核心数据对象 | 对象 | 含义 | 关键字段 | |------|------|---------| | Agent | 一个可连接的 Agent 实例 | id、name、runtime、status | | Session | 一条对话上下文 | id、agentId、title | | Message | 用户或 Agent 产生的内容 | id、sessionId、role、type、payload、timestamp | | Tool | App 端可被 Agent 调用的能力 | name、description、inputSchema、outputSchema | ### 3.4 与 MCP 的关系 - 工具协议层复用 MCP 的 `tools/list`、`tools/call` 定义方式 - 工具 Schema 格式遵循 MCP 的 JSON Schema 标准 - 通讯协议层和消息协议层是 MCP 未覆盖的部分——补充了远程安全双向传输的能力 ### 3.5 工具分类 详见独立文档 [tool-action-design.md](tool-action-design.md)——第一节"工具协议定义"。 | 决策 | 当期结论 | 后续扩展思路 | |------|---------|-------------| | 工具结构 | `{ name, type, description, actions[] }`(app/toolset)或 `{ name, type, description, inputSchema }`(action) | — | | app 生命周期 | open → use → close,通过 instance_id 维护 | — | | toolset 调用 | 每次独立,无状态 | — | | action 调用 | 只有一个 action,最简 | — | | 状态跟踪 | 依赖 Agent 自身对话上下文 | — | | 与 MCP 对应关系 | Tool = MCP Server,Action = MCP Tool | — | --- ## 四、第一版技术栈 | 端 | 选型 | |----|------| | Agent 插件 | 按 Agent 框架选择语言(Hermes 用 Python,OpenClaw 待定) | | App 端(Web) | 待定(Next.js / Vite + React) | | 通信方式 | WebSocket(裸 ws,不引入 Socket.io) | | 消息格式 | JSON | --- ## 五、MVP 边界 | 做 | 不做 | |----|------| | 局域网内 App 直连 Agent | 远程广域网连接 | | App 收发消息、查看 Agent 状态 | 任务生命周期管理 | | Agent 调 App 的工具(confirm/input 等) | 审批卡片系统 | | 简单的工具发现协议 | 多 Agent 编排、调度 | | 文本 + 富内容消息展示 | 通知推送 | | | 中转服务 | | | MCP 封装(第一期不做) | --- ## 六、一次完整的交互流程(以 choice 工具为例) ``` Agent 需要用户做选择 │ ├── Agent 发起 { type: "tool.call", payload: { name: "choice", call_id: "c1", arguments: { question: "部署到哪个环境?", options: ["测试", "预发布", "生产"] } } } │ ├── Agent 插件收到 → 通过 WebSocket 推给 App │ ├── App 渲染选择界面,三个选项展示给用户 │ ├── 用户点击"预发布" │ ├── App 通过 WebSocket 发回 { type: "tool.result", payload: { name: "choice", call_id: "c1", result: { message: "预发布" } } } │ ├── Agent 插件收到 → 交回给 Agent 核心 │ └── Agent 拿到结果,继续执行 ``` 关键原则: - App 端不关心 Agent 为什么问这个问题,只负责渲染和返回用户操作结果 - Agent 端不关心 App 用什么 UI 渲染的,只负责发起工具调用和处理返回结果 - 调用(Agent → App)和返回(App → Agent)都使用结构化消息,不是自然语言文本 - 整个交互走一条 WebSocket 连接,双向实时,消息协议统一 ### 6.1 消息方向与格式 所有消息使用统一信封:`{ v, id, type, payload }`。完整格式定义见 [tool-action-design.md](tool-action-design.md)——第二节"消息协议定义"。 --- ## 七、后续可能的扩展 - 加入中转服务,支持广域网远程连接 - 加入端到端加密,中转不可读消息内容 - 加入 mDNS 局域网自动发现(类似 Bonjour) - 移动端原生 App - 支持流式数据传输(如实时 SVG 渲染)