docs: finalize documentation cleanup

- Update OPENVIKING_INTEGRATION with latest status
- Remove outdated plan files (now archived in docs/archive/)
- Clean up redundant documentation

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
iven
2026-03-16 10:00:01 +08:00
parent a7582cb135
commit 721e400bd0
11 changed files with 78 additions and 4528 deletions

View File

@@ -429,6 +429,84 @@ cd desktop
pnpm vitest run tests/desktop/memory*.test.ts pnpm vitest run tests/desktop/memory*.test.ts
``` ```
## 火山引擎 (Volcengine) 配置
### 激活 Embedding 模型
**重要**:火山引擎的 Embedding 模型需要在控制台单独激活。
1. **登录火山引擎控制台**
https://console.volcengine.com/ark
2. **激活 Embedding 模型**
- 进入「模型推理」→「模型服务」
- 搜索并激活以下模型之一:
- `Doubao-Embedding` (推荐1024 维)
- `Doubao-Embedding-Large` (2048 维)
3. **获取 Endpoint ID**
- 激活后,复制模型的 **Endpoint ID**
- 格式类似:`ep-xxxxxxxxxxxx`
4. **更新配置文件**
使用 Endpoint ID推荐
```json
{
"embedding": {
"dense": {
"api_base": "https://ark.cn-beijing.volces.com/api/v3",
"api_key": "your-api-key",
"provider": "volcengine",
"model": "ep-xxxxxxxxxxxx",
"dimension": 1024
}
}
}
```
或使用模型名称(需要在控制台激活):
```json
{
"embedding": {
"dense": {
"api_base": "https://ark.cn-beijing.volces.com/api/v3",
"api_key": "your-api-key",
"provider": "volcengine",
"model": "doubao-embedding",
"dimension": 1024
}
}
}
```
### 常见错误
| 错误 | 原因 | 解决方案 |
|------|------|----------|
| `ModelNotOpen` | 模型未激活 | 在控制台激活对应的 Embedding 模型 |
| `InvalidEndpointOrModel.NotFound` | Endpoint ID 不存在 | 检查 Endpoint ID 是否正确 |
| `404 Not Found` | API 路径错误 | 确认 `api_base` 为 `https://ark.cn-beijing.volces.com/api/v3` |
### 测试 Embedding 配置
```bash
# 启动服务器后,测试向量搜索
curl -X POST http://127.0.0.1:1933/api/v1/search/search \
-H "Content-Type: application/json" \
-d '{"query": "test query", "limit": 5}'
```
成功响应:
```json
{"status":"ok","result":[],"error":null}
```
失败响应(需要激活模型):
```json
{"status":"error","error":{"message":"Volcengine embedding failed: ModelNotOpen..."}}
```
## 故障排除 ## 故障排除
### Q: OpenViking CLI not found ### Q: OpenViking CLI not found

View File

@@ -1,467 +0,0 @@
# ZCLAW 交付执行计划2026-03-12
## 1. 计划目标
本计划的目标不是继续做“功能堆叠”,而是把当前仓库推进到**可安装、可启动、可连接、可对话、可配置、可验证**的可交付状态。
当前对“完整可用 ZCLAW”的定义如下
- 用户能够在本机启动 ZCLAW 桌面应用
- 用户安装 ZCLAW 时OpenClaw 运行时已经随包提供,而不是要求用户另行安装
- 桌面应用能够引导并管理随 ZCLAW 一起分发的本地 OpenClaw Gateway
- 前端能够稳定连接 Gateway并完成基础握手与鉴权
- 用户能够创建、编辑、切换 AgentClone
- 用户能够发起真实对话并收到流式回复
- 关键设置页不再只是静态占位,而是尽量接到真实后端能力
- 有一套清晰的验收与收尾流程,支持阶段性提交与后续发布
---
## 2. 当前基线
### 2.1 已完成的关键能力
- Gateway 握手参数已修正,能够兼容 OpenClaw 2026.3.11
- Token 鉴权已接入前端连接流程
- `zclaw-ui` 插件可被 Gateway 正常加载
- Agent 的创建、编辑、保存链路已打通
- `scripts/setup.ts` 已可在已有 `~/.openclaw/openclaw.json` 时非破坏性合并插件与 skills 路径
- 自定义插件 manifest/package id 对齐问题已修复
### 2.2 当前仍阻塞交付的核心问题
按交付优先级排序,当前最关键的缺口为:
1. **桌面端尚未真正接管 Gateway 生命周期**
- `src/gateway/manager.ts` 已存在,但未被 Tauri 壳使用
- `desktop/src-tauri/src/lib.rs` 仍是默认模板
- 当前产品更像“前端连接外部 Gateway”还不是“完整桌面应用”
2. **当前仍默认依赖用户独立安装 OpenClaw**
- 这与最终产品目标不一致
- 最终必须做到:安装 ZCLAW 后即可直接使用 OpenClaw 能力
- 因此现阶段的 CLI/PATH 依赖只能作为开发期和过渡期方案
3. **真实桌面链路缺少本地运行闭环验证**
- 需要验证 Tauri 内从启动 Gateway 到连接、到拉数据、到发消息的完整过程
4. **设置体系中仍有若干页面/按钮处于占位状态**
- 部分页面已有 UI 但尚未连接真实能力
- 会影响“可用”判断,尤其是用户首次体验
5. **交付收尾缺少固定验收流程**
- 需要统一 smoke test、安装前检查、文档更新、阶段提交点
---
## 3. 总体推进策略
### 3.1 核心原则
- **先打通闭环,再做扩展**:优先修复阻塞真实使用的能力缺口,而不是继续加功能
- **优先最短交付路径**:优先复用 OpenClaw 现有 CLI/service 能力,而不是一开始就做完整 sidecar 架构
- **最终必须内置 OpenClaw**:开发阶段允许复用系统已安装的 OpenClaw但交付阶段必须改为随 ZCLAW 一起分发和托管
- **浏览器模式不回退**:新增 Tauri 能力必须有运行时保护,不影响现有浏览器预览/开发体验
- **阶段可提交**:每个阶段都有独立验收标准,达到后可形成 clean checkpoint
### 3.2 本轮优先级
- **P0**Tauri 桌面壳接入本地 Gateway 生命周期管理
- **P0**:完成真实桌面端基础闭环验证
- **P0**确定并落地“ZCLAW 安装即内置 OpenClaw”的分发方案
- **P1**:补齐最影响可用性的设置页占位项
- **P1**:形成交付前 smoke checklist 和文档更新
- **P2**:补测试、清理遗留代码、准备打包发布
---
## 4. 分阶段执行计划
## Phase A桌面端本地 Gateway 生命周期管理(当前最高优先级)
### A.1 目标
让 ZCLAW 桌面应用在 Tauri 环境下具备对本地 OpenClaw Gateway 的基础管理能力:
- 查询本地 Gateway 状态
- 启动本地 Gateway
- 停止本地 Gateway
- 重启本地 Gateway
- 在前端展示本地状态,并与现有 WebSocket 连接状态区分开
### A.2 实现策略
优先采用**Tauri Rust 命令封装 OpenClaw CLI** 的方式,而不是直接引入完整 sidecar
- Rust 侧封装以下命令:
- `openclaw gateway status --json`
- `openclaw gateway start --json`
- `openclaw gateway stop --json`
- `openclaw gateway restart --json`
- 前端通过 `invoke` 调用 Rust 命令
- 通过运行时判断,仅在 Tauri 环境中启用这组能力
- 浏览器模式继续保留“手工连接外部 Gateway”的现有逻辑
说明:
- 这一阶段是**开发期过渡方案**
- 它的价值是先把桌面端产品闭环跑通
- 但它**不是最终交付形态**
- 最终交付必须把 OpenClaw 运行时随 ZCLAW 一起打包,而不是要求用户本机已有 `openclaw`
### A.3 代码范围
- `desktop/src-tauri/src/lib.rs`
- `desktop/src/lib/tauri-gateway.ts`(新增)
- `desktop/src/store/gatewayStore.ts`
- `desktop/src/components/Settings/General.tsx`
- 如有必要:`desktop/src/components/RightPanel.tsx`
### A.4 验收标准
- Tauri 环境可正常调用本地 Gateway 管理命令
- 设置页能看到“本地 Gateway”状态卡片
- 用户可点击启动/停止/重启
- 启动成功后,前端可继续连接并拉取基础数据
- 浏览器模式不因该改动而报错或白屏
- 开发环境下,即使仍依赖系统 `openclaw`,也已经明确与最终 bundling 方案解耦
### A.5 风险与应对
- **风险**:不同机器上 `openclaw` 不在 PATH
- **应对**:前端明确提示“未安装 OpenClaw CLI”或“命令不可用”
- **风险**`status --json` / `start --json` 输出结构不稳定
- **应对**Rust 侧优先使用 `serde_json::Value` 宽松解析,再映射到前端稳定结构
- **风险**:服务模式与前台 `gateway run` 并存导致认知混乱
- **应对**UI 文案明确说明“本地服务状态”和“当前 WebSocket 连接状态”是两层状态
---
## Phase B真实桌面端基础闭环验证
### B.1 目标
确认 ZCLAW 在 Tauri 壳内已经不是“能打开 UI”而是“能完成一次真实任务闭环”
- 本地 Gateway 启动/可达
- 前端连接成功
- Clone 列表加载成功
- Agent 创建/编辑成功
- 首条消息发送成功
- 收到真实流式回复
### B.2 任务清单
- 启动桌面应用并检查本地 Gateway 状态
- 验证连接状态、版本、插件状态、workspace 信息是否能拉取
- 验证创建 Agent
- 验证编辑 Agent 并刷新右侧面板数据
- 验证 bootstrap 文件生成状态
- 验证聊天发送与回复流
- 记录关键报错与回退路径
### B.3 验收标准
- 至少完成一次完整桌面端对话闭环
- Agent 的创建与编辑在真实环境可用
- 连接失败、Gateway 未安装、未启动等错误能明确提示
- 关键路径没有阻塞性的控制台报错
---
## Phase COpenClaw 随包分发与运行时托管
### C.1 目标
把当前“依赖用户本机单独安装 OpenClaw”的开发态方案推进到真正可交付的产品方案
- 用户安装 ZCLAW 时OpenClaw 运行时已经包含在安装包内
- ZCLAW 启动后,能够直接找到并启动内置 OpenClaw
- 用户不需要再单独安装一套 OpenClaw CLI / 环境
### C.2 目标形态
最终交付建议采用以下形态:
- 安装包内包含 OpenClaw 可执行运行时或受控分发产物
- Tauri Rust 侧通过固定相对路径或 sidecar 机制调用该运行时
- ZCLAW 负责:
- 初始化 OpenClaw home / workspace
- 写入或合并默认配置
- 启动 / 停止 / 重启 Gateway
- 读取日志与状态
### C.3 方案比较
#### 方案 1继续依赖系统安装的 `openclaw`
优点:
- 当前开发改造最少
缺点:
- 不符合最终产品目标
- 用户安装体验差
- 环境差异和 PATH 问题会显著增加支持成本
结论:
- **仅适合开发期,不可作为最终交付方案**
#### 方案 2把 OpenClaw 作为 sidecar / bundled runtime 随 ZCLAW 分发
优点:
- 符合 QClaw / AutoClaw 式的一体化交付体验
- 可控性高
- 便于做安装后自启动、版本锁定、升级兼容
缺点:
- 需要处理体积、签名、跨平台打包、路径定位
结论:
- **这是最终推荐方案**
### C.4 实施任务
- 确认 OpenClaw 可分发形态
- npm 包直接落地
- 预构建二进制
- 内置 Node + OpenClaw 组合运行时
- 确认 Tauri 2 下 sidecar / bundled binary 的最佳实现方式
- 为 Windows 优先落地一版 bundling 方案
- 调整 Rust 侧命令执行逻辑
- 优先调用内置运行时
- 开发模式可回退到系统 `openclaw`
- 验证安装后首次启动流程
- 不依赖用户额外安装
- 可直接启动 Gateway
- 可连接、可聊天、可配置
### C.5 验收标准
- 全新机器上,未单独安装 OpenClaw 的情况下,可直接安装并启动 ZCLAW
- ZCLAW 可成功拉起内置 OpenClaw Gateway
- Agent / 聊天 / 设置等核心功能可正常工作
- 用户文档不再要求“先安装 OpenClaw 再使用 ZCLAW”
---
## Phase D设置页可用性补齐
### D.1 目标
梳理 Settings 体系中“看起来像功能、实际上还是占位”的部分,优先补齐最影响交付感知的项。
### D.2 优先补齐范围
优先级从高到低建议如下:
1. **General / ModelsAPI**
- Gateway 管理与连接语义统一
- 去掉误导性按钮或接到真实逻辑
2. **Workspace / Skills / MCPServices**
- 至少展示真实读取结果
- 对未支持能力明确标注“暂未接入”而不是伪交互
3. **IMChannels**
- 飞书状态尽量走真实探测
- 对未完成渠道使用明确状态说明
4. **Privacy / UsageStats / About**
- 以展示真实数据和静态说明为主,收尾体验
### D.3 判定标准
- 对用户可点击的动作,尽量有真实效果
- 对暂未接入的能力,明确说明而不是假按钮
- 页面不出现明显“假功能”感
---
## Phase E交付前 smoke test 与文档收尾
### E.1 目标
形成一套最小但明确的交付前检查流程,避免“本地看起来能用、别人拿到跑不起来”。
### E.2 交付前 smoke checklist
#### 环境检查
- `pnpm -v`
- `pnpm --dir desktop tauri --version`
说明:
- 最终交付 smoke test 不应再把系统级 `openclaw --version` 作为前置要求
- 应改为验证 ZCLAW 内置运行时是否可用
#### 桌面启动检查
- `pnpm --dir desktop tauri dev`
- UI 能正常打开
- 设置页不白屏
#### Gateway 闭环检查
- 本地 Gateway 状态可读
- 能启动/停止/重启
- 前端连接成功
#### 核心功能检查
- Clone 列表加载
- 新建 Clone
- 编辑 Clone
- 发送首条消息
- 收到流式回复
#### 配置检查
- quick config 可读写
- workspace 信息可读取
- 插件状态可显示
#### 安装闭环检查
- 全新环境中无需单独安装 OpenClaw
- 安装 ZCLAW 后首次启动即可使用
- 若内置运行时损坏或缺失,错误提示明确
### E.3 文档更新项
- 更新 README区分浏览器模式与 Tauri 桌面模式
- 补充本地 Gateway 启动/连接说明
- 补充已知限制与后续路线
-`PROGRESS.md` 中登记本轮交付成果
---
## Phase F交付后加强项不是当前阻塞项
以下事项重要,但不应阻塞本轮“完整可用”目标:
- 更完整的 Tauri sidecar / 进程托管架构
- 安装包/自动更新
- 更高覆盖率测试
- v1 归档代码清理
- 微信 / QQ Channel 扩展
- 新 Session Prompt 等增强功能
这些能力应在当前闭环稳定后进入下一轮计划。
---
## 5. 实施顺序与里程碑
## Milestone 1桌面端本地 Gateway 管理打通
输出物:
- Tauri 命令桥
- 前端本地 Gateway 状态卡片
- 启停/重启操作
完成标志:
- 能在桌面应用中看到并操作本地 Gateway 服务状态
## Milestone 2真实桌面闭环通过
输出物:
- 真实运行验证记录
- 阻塞 bug 列表(若有)
- 修复后的可用路径
完成标志:
- 从桌面打开到完成一次对话全链路可用
## Milestone 3OpenClaw 随包分发打通
输出物:
- Windows 优先的一体化 bundling 方案
- ZCLAW 优先调用内置 OpenClaw 运行时
- 安装后无需用户额外安装 OpenClaw 的可运行链路
完成标志:
- 在未安装 OpenClaw 的机器/环境中,安装 ZCLAW 后即可直接使用
## Milestone 4设置页与交付收尾
输出物:
- 最小可交付设置体验
- smoke checklist
- README / PROGRESS 更新
完成标志:
- 仓库进入“可给他人试用”的状态
---
## 6. 本轮立即执行项
按当前优先级,接下来立刻执行:
1. 在 Tauri Rust 侧实现 Gateway 管理命令
2. 在前端新增 Tauri Gateway bridge
3.`gatewayStore` 中接入本地 Gateway 状态与动作
4. 在 Settings > General 中增加本地 Gateway 管理卡片
5. 明确 OpenClaw 随包分发方案,避免把系统安装依赖固化为最终设计
6. 进行编译/运行级验证
7. 若验证通过,记录到 `PROGRESS.md`
---
## 7. 阶段提交策略
本轮按以下 checkpoint 推进:
### Checkpoint A
- 完成计划文档
- 完成 Tauri 命令桥与前端接线
### Checkpoint B
- 完成本地 Gateway 管理 UI
- 完成基础验证
### Checkpoint C
- 完成 OpenClaw bundling / sidecar 方案设计
- 明确 Windows 优先的交付路径
### Checkpoint D
- 完成设置页收尾 / 文档更新 / smoke checklist
说明:
- 代码会按干净阶段组织
- 如需执行远端 `push`,仍单独确认
---
## 8. 结论
当前最短、最正确的交付路径,不是继续扩展更多功能,而是先把 ZCLAW 从“能连 Gateway 的前端”推进成“能在桌面端真正管理并使用内置 OpenClaw 的产品”。
因此,本轮执行的核心结论是:
- **先做 Tauri 本地 Gateway 生命周期管理**
- **再完成 OpenClaw 随包分发方案**
- **然后做真实桌面端闭环验证**
- **最后收尾设置页与交付文档**
这条路线最符合当前仓库状态,也最接近“完整可用 ZCLAW”的真实交付目标。

View File

@@ -1,615 +0,0 @@
# ZCLAW UI/UX 全面优化计划
## 背景
ZCLAW 是基于 OpenFang (Rust Agent OS) 的 AI Agent 桌面客户端。经过 Phase 1-8 的功能开发,系统已达到 93% API 覆盖率和 100% UI 组件完成度。现在需要对前端设计元素进行全面优化,提升用户操作效率与视觉体验。
## 当前状态分析
### 代码结构
- **框架**: React 18 + TypeScript + Tauri
- **样式**: Tailwind CSS v4.2.1
- **状态管理**: Zustand (gatewayStore, chatStore, teamStore)
- **图标**: lucide-react
- **组件数量**: 37 个组件
### 现有设计特点
- **主色调**: Orange (#f97316) 作为品牌色
- **布局**: 三栏式 (Sidebar w-64 | Main flex-1 | RightPanel w-80)
- **暗黑模式**: 部分支持 (部分组件有 `dark:` 变体)
- **动画**: 基础 CSS 动画 (animate-pulse, animate-spin)
---
## 发现的问题
### 1. 设计系统问题 (CRITICAL)
| 问题 | 位置 | 影响 |
|------|------|------|
| 无 UI 组件库 | 全局 | 一致性差,重复代码 |
| 颜色系统不完整 | index.css | 品牌识别度低 |
| 暗黑模式不完整 | 多个组件 | 用户体验不一致 |
| **使用 Emoji 作为 UI 图标** | ChatArea, App.tsx | 不专业,违反设计规范 |
### 2. 可访问性问题 (CRITICAL)
| 问题 | 位置 | 影响 |
|------|------|------|
| 缺少 aria-label | 图标按钮 | 屏幕阅读器无法识别 |
| 焦点状态不明显 | 多个交互元素 | 键盘导航困难 |
| 颜色对比度不足 | text-gray-400 类 | 可读性差 |
### 3. 交互与动画 (HIGH)
| 问题 | 位置 | 影响 |
|------|------|------|
| 无过渡动画库 | 全局 | 交互生硬 |
| 悬停状态不一致 | 多个组件 | 用户困惑 |
| 缺少骨架屏 | 数据加载 | 感知性能差 |
### 4. 视觉层次 (MEDIUM)
| 问题 | 位置 | 影响 |
|------|------|------|
| 卡片阴影过轻 | shadow-sm | 层次不明显 |
| 间距不一致 | padding/margin | 视觉混乱 |
| 字体过小 | text-xs | 可读性差 |
### 5. 用户体验 (MEDIUM)
| 问题 | 位置 | 影响 |
|------|------|------|
| 空状态设计简陋 | 多个列表 | 缺乏引导 |
| 错误提示不明显 | 表单等 | 用户困惑 |
| 加载反馈不足 | API 调用 | 用户焦虑 |
---
## 用户确认的优化方向
| 决策项 | 选择 |
|--------|------|
| 动画库 | ✅ 引入 Framer Motion |
| 暗黑模式 | ✅ 完整支持所有组件 |
| 组件库 | ✅ 创建 Button, Card, Input 等基础组件 |
---
## 优化方案
### Phase 1: 设计系统建立 (P0)
#### 1.1 CSS 变量系统
**文件**: `desktop/src/index.css`
```css
:root {
/* Brand Colors */
--color-primary: #f97316;
--color-primary-hover: #ea580c;
--color-primary-light: #fff7ed;
/* Semantic Colors */
--color-success: #22c55e;
--color-warning: #eab308;
--color-error: #ef4444;
--color-info: #3b82f6;
/* Neutral Colors */
--color-bg: #ffffff;
--color-bg-secondary: #f9fafb;
--color-border: #e5e7eb;
--color-text: #111827;
--color-text-secondary: #6b7280;
--color-text-muted: #9ca3af;
/* Spacing Scale */
--space-xs: 4px;
--space-sm: 8px;
--space-md: 16px;
--space-lg: 24px;
--space-xl: 32px;
/* Border Radius */
--radius-sm: 6px;
--radius-md: 8px;
--radius-lg: 12px;
--radius-xl: 16px;
--radius-full: 9999px;
/* Shadows */
--shadow-sm: 0 1px 2px 0 rgb(0 0 0 / 0.05);
--shadow-md: 0 4px 6px -1px rgb(0 0 0 / 0.1);
--shadow-lg: 0 10px 15px -3px rgb(0 0 0 / 0.1);
/* Transitions */
--transition-fast: 150ms ease;
--transition-normal: 200ms ease;
--transition-slow: 300ms ease;
}
.dark {
--color-bg: #0f172a;
--color-bg-secondary: #1e293b;
--color-border: #334155;
--color-text: #f1f5f9;
--color-text-secondary: #94a3b8;
--color-text-muted: #64748b;
}
```
#### 1.2 统一 Tailwind 配置
**文件**: `desktop/tailwind.config.js` (新建)
```javascript
export default {
theme: {
extend: {
colors: {
primary: {
DEFAULT: 'var(--color-primary)',
hover: 'var(--color-primary-hover)',
light: 'var(--color-primary-light)',
},
},
boxShadow: {
'card': 'var(--shadow-md)',
'hover': 'var(--shadow-lg)',
},
transitionDuration: {
'fast': '150ms',
'normal': '200ms',
},
},
},
}
```
### Phase 2: 基础组件库 (P0)
#### 2.1 Button 组件
**文件**: `desktop/src/components/ui/Button.tsx`
```tsx
import { forwardRef } from 'react';
import { motion } from 'framer-motion';
import { cn } from '../../lib/utils';
interface ButtonProps extends React.ButtonHTMLAttributes<HTMLButtonElement> {
variant?: 'primary' | 'secondary' | 'ghost' | 'danger';
size?: 'sm' | 'md' | 'lg';
loading?: boolean;
}
export const Button = forwardRef<HTMLButtonElement, ButtonProps>(
({ className, variant = 'primary', size = 'md', loading, children, disabled, ...props }, ref) => {
return (
<motion.button
ref={ref}
whileTap={{ scale: 0.98 }}
className={cn(
'inline-flex items-center justify-center font-medium rounded-lg transition-colors',
'focus:outline-none focus-visible:ring-2 focus-visible:ring-primary focus-visible:ring-offset-2',
'disabled:opacity-50 disabled:cursor-not-allowed',
variants[variant],
sizes[size],
className
)}
disabled={disabled || loading}
{...props}
>
{loading && <Spinner className="mr-2" />}
{children}
</motion.button>
);
}
);
const variants = {
primary: 'bg-primary text-white hover:bg-primary-hover',
secondary: 'bg-gray-100 text-gray-900 hover:bg-gray-200',
ghost: 'text-gray-600 hover:bg-gray-100',
danger: 'bg-red-500 text-white hover:bg-red-600',
};
const sizes = {
sm: 'px-3 py-1.5 text-xs',
md: 'px-4 py-2 text-sm',
lg: 'px-6 py-3 text-base',
};
```
#### 2.2 Card 组件
**文件**: `desktop/src/components/ui/Card.tsx`
```tsx
import { motion } from 'framer-motion';
import { cn } from '../../lib/utils';
interface CardProps {
children: React.ReactNode;
className?: string;
hoverable?: boolean;
onClick?: () => void;
}
export function Card({ children, className, hoverable, onClick }: CardProps) {
const Component = hoverable ? motion.div : 'div';
return (
<Component
className={cn(
'rounded-xl border border-gray-200 bg-white p-4 shadow-sm',
'dark:border-gray-700 dark:bg-gray-800',
hoverable && 'cursor-pointer hover:shadow-md transition-shadow duration-200',
className
)}
{...(hoverable && {
whileHover: { y: -2 },
onClick,
})}
>
{children}
</Component>
);
}
```
#### 2.3 cn() 工具函数
**文件**: `desktop/src/lib/utils.ts`
```typescript
import { clsx, type ClassValue } from 'clsx';
import { twMerge } from 'tailwind-merge';
export function cn(...inputs: ClassValue[]) {
return twMerge(clsx(inputs));
}
```
**原则**: 使用 SVG 图标 (lucide-react),不使用 emoji 作为 UI 元素
| 文件 | 当前 | 修改为 |
|------|------|--------|
| `ChatArea.tsx:79` | `🤖` | `<BotIcon className="w-10 h-10 text-gray-400" />` |
| `ChatArea.tsx:279` | `🦞` (消息气泡) | `<ZClawLogo className="w-6 h-6" />` (自定义图标) |
| `App.tsx:79` | `🤖` | `<BotIcon />` |
| `App.tsx:98` | `👥` | `<UsersIcon />` |
| `Sidebar.tsx:98` | 用户头像 emoji | 首字母 + 渐变背景 |
### Phase 3: 可访问性改进 (P0)
#### 3.1 添加 aria-label
**关键文件**:
- `Sidebar.tsx` - 设置按钮、tab 切换
- `ChatArea.tsx` - 发送按钮、附件按钮、模型选择器
- `RightPanel.tsx` - tab 切换、刷新按钮
- `SettingsLayout.tsx` - 返回按钮、菜单项
```tsx
// 示例修复
<button
onClick={onOpenSettings}
aria-label="打开设置"
className="..."
>
<Settings className="w-4 h-4" />
</button>
```
#### 3.2 焦点状态增强
```css
/* 全局焦点样式 */
:focus-visible {
outline: 2px solid var(--color-primary);
outline-offset: 2px;
}
/* 按钮焦点 */
.btn:focus-visible {
ring: 2px;
ring-color: var(--color-primary);
ring-offset: 2px;
}
```
#### 3.3 颜色对比度修复
| 当前 | 对比度 | 修复 |
|------|--------|------|
| `text-gray-400` on white | 3.1:1 (FAIL) | 改为 `text-gray-500` (#6b7280) 4.6:1 |
| `text-gray-300` on white | 2.9:1 (FAIL) | 改为 `text-gray-600` (#4b5563) 7.0:1 |
### Phase 4: 交互与动画增强 (P1)
#### 4.1 Framer Motion 动画系统
**新文件**: `desktop/src/lib/animations.ts`
```typescript
import { Variants } from 'framer-motion';
// 页面切换动画
export const pageVariants: Variants = {
initial: { opacity: 0, y: 10 },
animate: { opacity: 1, y: 0 },
exit: { opacity: 0, y: -10 },
};
// 列表项交错动画
export const listItemVariants: Variants = {
hidden: { opacity: 0, x: -10 },
visible: { opacity: 1, x: 0 },
};
// 按钮点击动画
export const buttonTap = { scale: 0.98 };
// 卡片悬停动画
export const cardHover = { y: -2, boxShadow: '0 10px 25px -5px rgb(0 0 0 / 0.1)' };
// 默认过渡配置
export const defaultTransition = {
duration: 0.2,
ease: [0.4, 0, 0.2, 1],
};
```
**使用示例**:
```tsx
import { motion, AnimatePresence } from 'framer-motion';
import { pageVariants, defaultTransition } from '../lib/animations';
// 页面切换
<AnimatePresence mode="wait">
<motion.div
key={view}
variants={pageVariants}
initial="initial"
animate="animate"
exit="exit"
transition={defaultTransition}
>
{content}
</motion.div>
</AnimatePresence>
```
**新文件**: `desktop/src/components/ui/Skeleton.tsx`
```tsx
export function Skeleton({ className }: { className?: string }) {
return (
<div
className={cn(
"animate-pulse bg-gray-200 dark:bg-gray-700 rounded",
className
)}
/>
);
}
export function CardSkeleton() {
return (
<div className="rounded-xl border border-gray-200 p-4">
<Skeleton className="h-4 w-24 mb-3" />
<Skeleton className="h-3 w-full mb-2" />
<Skeleton className="h-3 w-3/4" />
</div>
);
}
```
#### 4.3 Toast 通知系统
**新文件**: `desktop/src/components/ui/Toast.tsx`
用于替代 `alert()` 和内联错误消息。
### Phase 5: 视觉层次优化 (P1)
#### 5.1 卡片阴影增强
```diff
- className="rounded-xl border border-gray-200 bg-white p-4 shadow-sm"
+ className="rounded-xl border border-gray-200 bg-white p-4 shadow-sm hover:shadow-md transition-shadow duration-200"
```
#### 5.2 间距标准化
| 区域 | 当前 | 标准 |
|------|------|------|
| 页面内边距 | 不一致 | `p-6` (24px) |
| 卡片内边距 | `p-3`/`p-4` | `p-4` (16px) |
| 列表项间距 | `space-y-1`/`space-y-2` | `space-y-2` (8px) |
| 区域间距 | `space-y-3`/`space-y-4` | `space-y-4` (16px) |
#### 5.3 字体大小优化
| 类型 | 当前 | 建议 |
|------|------|------|
| 正文 | `text-xs` (12px) | `text-sm` (14px) |
| 小标签 | `text-[10px]` | `text-xs` (12px) |
| 标题 | `text-lg` | 保持 |
### Phase 6: 用户体验改进 (P2)
#### 6.1 空状态设计
**新组件**: `EmptyState.tsx`
```tsx
interface EmptyStateProps {
icon: React.ReactNode;
title: string;
description: string;
action?: React.ReactNode;
}
export function EmptyState({ icon, title, description, action }: EmptyStateProps) {
return (
<div className="flex-1 flex items-center justify-center p-6">
<div className="text-center max-w-sm">
<div className="w-16 h-16 bg-gray-100 dark:bg-gray-800 rounded-full flex items-center justify-center mx-auto mb-4 text-gray-400">
{icon}
</div>
<h3 className="text-base font-semibold text-gray-700 dark:text-gray-300 mb-2">
{title}
</h3>
<p className="text-sm text-gray-500 dark:text-gray-400 mb-4">
{description}
</p>
{action}
</div>
</div>
);
}
```
#### 6.2 错误状态设计
- 使用红色边框和背景
- 显示错误图标
- 提供重试按钮
#### 6.3 加载状态改进
- 按钮加载时禁用并显示 spinner
- 列表加载时显示骨架屏
- 全局加载时显示顶部进度条
---
## 实施顺序
### 阶段 1: 基础设施 (2-3 天)
1. 安装依赖: `framer-motion clsx tailwind-merge`
2. 创建 CSS 变量系统 (含完整暗黑模式)
3. 创建 tailwind.config.js
4. 创建 utils.ts (cn 函数)
5. 创建 animations.ts (Framer Motion 预设)
### 阶段 2: 基础组件库 (2-3 天)
1. 创建 Button 组件 (含变体: primary, secondary, ghost)
2. 创建 Card 组件 (含悬停动画)
3. 创建 Input 组件 (含焦点状态)
4. 创建 Badge 组件
5. 创建 Skeleton 组件
6. 创建 EmptyState 组件
7. 创建 Toast 组件
### 阶段 3: 可访问性修复 (1-2 天)
1. 添加 aria-label 到所有图标按钮
2. 修复颜色对比度问题
3. 增强焦点状态
4. 添加键盘导航支持
### 阶段 4: 视觉优化 (2-3 天)
1. 移除所有 emoji 图标,替换为 SVG
2. 使用基础组件库重构现有组件
3. 标准化间距
4. 增强卡片阴影和悬停效果
5. 完善暗黑模式支持
### 阶段 5: 交互增强 (2-3 天)
1. 添加 Framer Motion 页面切换动画
2. 添加列表项动画 (stagger)
3. 添加按钮点击反馈
4. 实现骨架屏加载
5. 集成 Toast 通知系统
### 阶段 6: 组件重构 (2-3 天)
1. 重构 Sidebar 组件 (使用新组件库 + 动画)
2. 重构 ChatArea 组件
3. 重构 RightPanel 组件
4. 重构 SettingsLayout 组件
5. 完整暗黑模式测试
---
## 关键文件清单
### 需要修改的文件
| 文件 | 修改内容 |
|------|----------|
| `desktop/src/index.css` | 添加 CSS 变量系统 |
| `desktop/src/components/Sidebar.tsx` | aria-label, 动画, emoji 移除 |
| `desktop/src/components/ChatArea.tsx` | aria-label, emoji 移除, 空状态 |
| `desktop/src/components/RightPanel.tsx` | aria-label, 间距标准化 |
| `desktop/src/components/Settings/SettingsLayout.tsx` | aria-label, 间距标准化 |
| `desktop/src/App.tsx` | emoji 移除, 空状态组件 |
### 需要新建的文件
| 文件 | 用途 |
|------|------|
| `desktop/tailwind.config.js` | Tailwind 自定义配置 |
| `desktop/src/components/ui/Button.tsx` | 按钮组件 |
| `desktop/src/components/ui/Card.tsx` | 卡片组件 |
| `desktop/src/components/ui/Input.tsx` | 输入框组件 |
| `desktop/src/components/ui/Badge.tsx` | 标签组件 |
| `desktop/src/components/ui/Skeleton.tsx` | 骨架屏组件 |
| `desktop/src/components/ui/EmptyState.tsx` | 空状态组件 |
| `desktop/src/components/ui/Toast.tsx` | Toast 通知组件 |
| `desktop/src/lib/utils.ts` | cn() 工具函数 |
| `desktop/src/lib/animations.ts` | Framer Motion 动画预设 |
### 需要安装的依赖
```bash
cd desktop
pnpm add framer-motion clsx tailwind-merge
```
---
## 验证方法
### 1. 视觉验证
```bash
pnpm tauri:dev
```
- 检查所有页面在浅色/深色模式下的显示
- 检查所有交互元素的悬停状态
- 检查所有空状态的显示
### 2. 可访问性验证
- 使用 Chrome DevTools Lighthouse 进行可访问性审计
- 使用 Tab 键进行键盘导航测试
- 使用屏幕阅读器测试 (NVDA/JAWS)
### 3. 类型检查
```bash
cd desktop && pnpm tsc --noEmit
```
### 4. 构建验证
```bash
pnpm build
```
---
## 预期成果
1. **设计系统**: 完整的 CSS 变量和 Tailwind 配置
2. **组件库**: 7 个可复用 UI 组件 (Button, Card, Input, Badge, Skeleton, EmptyState, Toast)
3. **可访问性**: Lighthouse 可访问性分数 > 90
4. **暗黑模式**: 所有组件完整支持暗黑模式
5. **动画系统**: Framer Motion 动画预设和页面过渡
6. **视觉一致性**: 所有组件遵循统一设计规范
7. **无 Emoji**: 所有 UI 图标使用 SVG
---
*计划创建: 2026-03-15*
*预计完成: 11-17 个工作日*

View File

@@ -1,663 +0,0 @@
# OpenFang Hands & Workflow 集成开发方案
## 上下文
**目标**: 将 OpenFang 的 Hands 和 Workflow 功能深度集成到 ZClaw 桌面客户端,提供与 OpenFang Web 界面对等的用户体验。
**当前状态**:
- ZClaw 已有基础的 `HandsPanel.tsx``WorkflowList.tsx` 组件
- 这些组件功能有限,缺少 OpenFang 的核心 UI 特性
- OpenFang v0.4.0 提供了 8 个 Hands 和完整的 Workflow/Scheduler 系统
**参考界面**: http://127.0.0.1:50051 (OpenFang Dashboard)
---
## 一、OpenFang 界面分析总结
### 1.1 Hands 页面设计
```
┌─────────────────────────────────────────────────────────────────┐
│ Hands — Curated Autonomous Capability Packages │
│ Available 8 Active │
├─────────────────────────────────────────────────────────────────┤
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ 🌐 Browser Hand [READY] │ │
│ │ Autonomous web browser — navigates sites... │ │
│ │ │ │
│ │ REQUIREMENTS │ │
│ │ ✓ Python 3 must be installed │ │
│ │ ✓ Chromium or Google Chrome must be installed │ │
│ │ │ │
│ │ 18 tool(s) · 3 metric(s) [productivity] │ │
│ │ [Details] [Activate] │ │
│ └─────────────────────────────────────────────────────────┘ │
└─────────────────────────────────────────────────────────────────┘
```
**详情弹窗内容**:
- AGENT CONFIG: Provider, Model
- REQUIREMENTS: 检查项和状态 (✓/✗)
- TOOLS: 工具名称列表
- DASHBOARD METRICS: 指标名称列表
- Activate 按钮
### 1.2 Workflows 页面设计
```
┌─────────────────────────────────────────────────────────────────┐
│ Workflows │
│ What are Workflows? Workflows chain multiple agents... │
│ [List] [Visual Builder] [+ New Workflow] │
├─────────────────────────────────────────────────────────────────┤
│ NAME │ STEPS │ CREATED │ ACTIONS │
│ ──────────────────┼───────┼──────────────┼────────────────────│
│ 测试工作流 │ 1 │ 2026/3/14 │ [Run][Edit][Del] │
└─────────────────────────────────────────────────────────────────┘
```
### 1.3 Scheduler 页面设计
```
┌─────────────────────────────────────────────────────────────────┐
│ Scheduler [+ New Job] │
│ [Scheduled Jobs] [Event Triggers] [Run History] │
├─────────────────────────────────────────────────────────────────┤
│ Scheduled Jobs │
│ Create cron-based scheduled jobs... │
│ │
│ [No scheduled jobs] │
│ Create a cron job to run agents on a recurring schedule. │
│ [+ Create Scheduled Job] │
└─────────────────────────────────────────────────────────────────┘
```
### 1.4 Approvals 页面设计
```
┌─────────────────────────────────────────────────────────────────┐
│ Execution Approvals [Refresh] │
│ [All] [Pending] [Approved] [Rejected] │
├─────────────────────────────────────────────────────────────────┤
│ [No approvals] │
│ When agents request permission for sensitive actions, │
│ they'll appear here. │
└─────────────────────────────────────────────────────────────────┘
```
---
## 二、ZClaw 现有实现分析
### 2.1 已有组件
| 文件 | 功能 | 完成度 |
|------|------|--------|
| `HandsPanel.tsx` | Hand 列表、触发、审批、取消 | 40% |
| `WorkflowList.tsx` | Workflow 列表、执行 | 30% |
| `TriggersPanel.tsx` | Trigger 列表 | 20% |
| `gatewayStore.ts` | 状态管理 (Hands/Workflow API) | 60% |
### 2.2 缺失功能
1. **Hands**:
- ❌ 详情弹窗 (Details Modal)
- ❌ Requirements 状态检查可视化
- ❌ 工具和指标列表展示
- ❌ Agent Config 显示 (Provider/Model)
- ❌ 激活动画和状态反馈
- ❌ 分类标签 (productivity/data/content/communication)
2. **Workflows**:
- ❌ 创建/编辑 Workflow
- ❌ Visual Builder
- ❌ 执行历史查看
- ❌ 步骤详情展示
3. **Scheduler**:
- ❌ Scheduled Jobs 管理
- ❌ Event Triggers 管理
- ❌ Cron 表达式编辑器
- ❌ Run History
4. **Approvals**:
- ❌ 独立 Approvals 页面
- ❌ 筛选功能 (All/Pending/Approved/Rejected)
- ❌ 审批详情展示
---
## 三、开发方案
### 3.1 Phase 1: 增强 HandsPanel (优先级: 高)
**目标**: 提供与 OpenFang 对等的 Hands 管理体验
**文件修改**:
- `desktop/src/components/HandsPanel.tsx` (重写)
- `desktop/src/components/HandDetailsModal.tsx` (新建)
- `desktop/src/store/gatewayStore.ts` (扩展)
**UI 设计**:
```tsx
// HandCard 组件结构
<div className="hand-card">
<div className="hand-header">
<span className="hand-icon">{hand.icon}</span>
<h3>{hand.name}</h3>
<StatusBadge status={hand.status} /> {/* READY/SETUP NEEDED/RUNNING */}
</div>
<p className="hand-description">{hand.description}</p>
{/* Requirements 检查 */}
{hand.requirements && (
<div className="hand-requirements">
<span className="label">REQUIREMENTS</span>
{hand.requirements.map(req => (
<div className={req.met ? 'met' : 'unmet'}>
<span>{req.met ? '✓' : '✗'}</span>
<span>{req.description}</span>
</div>
))}
</div>
)}
{/* 元信息 */}
<div className="hand-meta">
<span>{hand.toolCount} tool(s)</span>
<span>{hand.metricCount} metric(s)</span>
<span className="category-tag">{hand.category}</span>
</div>
{/* 操作按钮 */}
<div className="hand-actions">
<Button variant="outline" onClick={onDetails}>Details</Button>
<Button variant="primary" onClick={onActivate} disabled={!hand.requirementsMet}>
{hand.status === 'running' ? 'Running...' : 'Activate'}
</Button>
</div>
</div>
```
**HandDetailsModal 组件**:
```tsx
// 详情弹窗
<Modal>
<ModalHeader>
<span className="icon">{hand.icon}</span>
<h2>{hand.name}</h2>
<StatusBadge status={hand.status} />
</ModalHeader>
<ModalBody>
{/* Agent Config */}
<Section title="AGENT CONFIG">
<Row label="Provider" value={hand.provider} />
<Row label="Model" value={hand.model} />
</Section>
{/* Requirements */}
<Section title="REQUIREMENTS">
{hand.requirements.map(req => (
<RequirementItem {...req} />
))}
</Section>
{/* Tools */}
<Section title="TOOLS">
<ToolGrid tools={hand.tools} />
</Section>
{/* Dashboard Metrics */}
<Section title="DASHBOARD METRICS">
<MetricList metrics={hand.metrics} />
</Section>
</ModalBody>
<ModalFooter>
<Button variant="outline" onClick={onClose}>Close</Button>
<Button variant="primary" onClick={onActivate}>Activate</Button>
</ModalFooter>
</Modal>
```
**API 扩展**:
```typescript
// gatewayStore.ts 扩展
interface Hand {
id: string;
name: string;
description: string;
status: 'idle' | 'running' | 'needs_approval' | 'error' | 'unavailable';
icon?: string;
category?: string; // productivity, data, content, communication
provider?: string;
model?: string;
requirements?: Array<{
description: string;
met: boolean;
details?: string;
}>;
tools?: string[];
metrics?: string[];
toolCount?: number;
metricCount?: number;
currentRunId?: string;
}
// 新增 API 调用
getHandDetails: (name: string) => Promise<HandDetails>;
activateHand: (name: string, params?: Record<string, unknown>) => Promise<HandRun>;
deactivateHand: (name: string) => Promise<void>;
```
### 3.2 Phase 2: 增强 WorkflowList (优先级: 高)
**目标**: 提供完整的 Workflow 管理能力
**文件修改**:
- `desktop/src/components/WorkflowList.tsx` (重写)
- `desktop/src/components/WorkflowEditor.tsx` (新建)
- `desktop/src/components/WorkflowHistory.tsx` (新建)
- `desktop/src/store/gatewayStore.ts` (扩展)
**UI 设计**:
```tsx
// WorkflowList 组件结构
<div className="workflow-list">
<div className="workflow-header">
<h2>Workflows</h2>
<div className="view-toggle">
<Button active={view === 'list'}>List</Button>
<Button active={view === 'visual'}>Visual Builder</Button>
</div>
<Button variant="primary" onClick={onCreate}>+ New Workflow</Button>
</div>
<p className="workflow-description">
Workflows chain multiple agents into automated pipelines...
</p>
<table className="workflow-table">
<thead>
<tr>
<th>NAME</th>
<th>STEPS</th>
<th>CREATED</th>
<th>ACTIONS</th>
</tr>
</thead>
<tbody>
{workflows.map(wf => (
<tr key={wf.id}>
<td>{wf.name}</td>
<td>{wf.steps}</td>
<td>{formatDate(wf.createdAt)}</td>
<td>
<Button size="sm" onClick={() => onRun(wf.id)}>Run</Button>
<Button size="sm" onClick={() => onEdit(wf.id)}>Edit</Button>
<Button size="sm" onClick={() => onHistory(wf.id)}>History</Button>
<Button size="sm" variant="danger" onClick={() => onDelete(wf.id)}>Delete</Button>
</td>
</tr>
))}
</tbody>
</table>
</div>
```
**WorkflowEditor 组件** (简化版):
```tsx
<WorkflowEditor workflow={workflow}>
<div className="workflow-editor">
<div className="workflow-info">
<Input label="Name" value={workflow.name} onChange={...} />
<Textarea label="Description" value={workflow.description} onChange={...} />
</div>
<div className="workflow-steps">
<h3>Steps</h3>
{workflow.steps.map((step, index) => (
<WorkflowStep
key={index}
step={step}
onEdit={() => editStep(index)}
onDelete={() => deleteStep(index)}
/>
))}
<Button onClick={addStep}>+ Add Step</Button>
</div>
<div className="workflow-actions">
<Button variant="outline" onClick={onCancel}>Cancel</Button>
<Button variant="primary" onClick={onSave}>Save Workflow</Button>
</div>
</div>
</WorkflowEditor>
```
**API 扩展**:
```typescript
// gatewayStore.ts 扩展
interface Workflow {
id: string;
name: string;
description?: string;
steps: WorkflowStep[];
createdAt: string;
updatedAt?: string;
}
interface WorkflowStep {
id: string;
agentId: string;
promptTemplate: string;
inputMapping?: Record<string, string>;
outputMapping?: Record<string, string>;
condition?: string;
timeout?: number;
}
// 新增 API 调用
createWorkflow: (workflow: CreateWorkflowInput) => Promise<Workflow>;
updateWorkflow: (id: string, updates: Partial<Workflow>) => Promise<Workflow>;
getWorkflowHistory: (id: string) => Promise<WorkflowRun[]>;
getWorkflowDetails: (id: string) => Promise<Workflow>;
```
### 3.3 Phase 3: 新建 SchedulerPanel (优先级: 中)
**目标**: 提供定时任务和事件触发器管理
**文件新建**:
- `desktop/src/components/SchedulerPanel.tsx`
- `desktop/src/components/ScheduledJobEditor.tsx`
- `desktop/src/components/EventTriggerEditor.tsx`
**UI 设计**:
```tsx
<SchedulerPanel>
<Tabs defaultValue="scheduled">
<TabsList>
<TabsTrigger value="scheduled">Scheduled Jobs</TabsTrigger>
<TabsTrigger value="triggers">Event Triggers</TabsTrigger>
</TabsList>
<TabsContent value="scheduled">
<div className="scheduled-jobs">
<Button onClick={onCreateJob}>+ Create Scheduled Job</Button>
{jobs.length === 0 ? (
<EmptyState
title="No scheduled jobs"
description="Create a cron job to run agents on a recurring schedule."
action="+ Create Scheduled Job"
onAction={onCreateJob}
/>
) : (
<JobList jobs={jobs} onEdit={onEditJob} onDelete={onDeleteJob} />
)}
</div>
</TabsContent>
<TabsContent value="triggers">
<div className="event-triggers">
<p>Event triggers fire agents in response to system events...</p>
{triggers.length === 0 ? (
<EmptyState title="No event triggers" />
) : (
<TriggerList triggers={triggers} />
)}
</div>
</TabsContent>
</Tabs>
</SchedulerPanel>
```
### 3.4 Phase 4: 新建 ApprovalsPanel (优先级: 中)
**目标**: 提供审批管理界面
**文件新建**:
- `desktop/src/components/ApprovalsPanel.tsx`
**UI 设计**:
```tsx
<ApprovalsPanel>
<div className="approvals-header">
<h2>Execution Approvals</h2>
<Button onClick={onRefresh}>Refresh</Button>
</div>
<div className="approvals-filters">
<Button active={filter === 'all'}>All</Button>
<Button active={filter === 'pending'}>Pending</Button>
<Button active={filter === 'approved'}>Approved</Button>
<Button active={filter === 'rejected'}>Rejected</Button>
</div>
<div className="approvals-list">
{filteredApprovals.length === 0 ? (
<EmptyState
title="No approvals"
description="When agents request permission for sensitive actions, they'll appear here."
/>
) : (
filteredApprovals.map(approval => (
<ApprovalCard
key={approval.id}
approval={approval}
onApprove={() => onApprove(approval.id)}
onReject={() => onReject(approval.id)}
/>
))
)}
</div>
</ApprovalsPanel>
```
### 3.5 Phase 5: 导航重构 (优先级: 中)
**目标**: 重构导航结构,匹配 OpenFang 布局
**文件修改**:
- `desktop/src/components/Sidebar.tsx`
- `desktop/src/components/RightPanel.tsx`
- `desktop/src/App.tsx`
**新导航结构**:
```
┌────────────────────┐
│ ZCLAW │
├────────────────────┤
│ CHAT │
│ └─ Chat │
│ MONITOR │
│ └─ Overview │
│ └─ Analytics │
│ └─ Logs │
│ AGENTS │
│ └─ Sessions │
│ └─ Approvals │
│ └─ Comms │
│ AUTOMATION │
│ └─ Workflows │
│ └─ Scheduler │
│ EXTENSIONS │
│ └─ Channels │
│ └─ Skills │
│ └─ Hands │
│ SYSTEM │
│ └─ Runtime │
│ └─ Settings │
└────────────────────┘
```
---
## 四、关键文件清单
### 4.1 需要修改的文件
| 文件路径 | 修改内容 |
|----------|----------|
| `desktop/src/components/HandsPanel.tsx` | 重写 HandCard添加详情弹窗 |
| `desktop/src/components/WorkflowList.tsx` | 添加创建/编辑功能 |
| `desktop/src/store/gatewayStore.ts` | 扩展 Hand/Workflow 类型定义 |
| `desktop/src/components/Sidebar.tsx` | 重构导航结构 |
| `desktop/src/components/RightPanel.tsx` | 集成新组件 |
| `desktop/src/lib/gateway-client.ts` | 添加新 API 调用 |
### 4.2 需要新建的文件
| 文件路径 | 功能 |
|----------|------|
| `desktop/src/components/HandDetailsModal.tsx` | Hand 详情弹窗 |
| `desktop/src/components/WorkflowEditor.tsx` | Workflow 编辑器 |
| `desktop/src/components/WorkflowHistory.tsx` | Workflow 执行历史 |
| `desktop/src/components/SchedulerPanel.tsx` | Scheduler 管理面板 |
| `desktop/src/components/ScheduledJobEditor.tsx` | 定时任务编辑器 |
| `desktop/src/components/EventTriggerEditor.tsx` | 事件触发器编辑器 |
| `desktop/src/components/ApprovalsPanel.tsx` | 审批管理面板 |
---
## 五、验证方案
### 5.1 手动测试
1. **Hands 测试**:
- 启动 ZClaw连接 OpenFang (端口 50051)
- 打开 Hands 标签
- 验证 8 个 Hands 正确显示
- 点击 Details 查看详情弹窗
- 点击 Activate 激活一个 Hand
- 验证状态变化和反馈
2. **Workflow 测试**:
- 打开 Workflow 标签
- 创建新 Workflow
- 编辑 Workflow 步骤
- 执行 Workflow
- 查看执行历史
3. **Scheduler 测试**:
- 创建定时任务
- 编辑 Cron 表达式
- 验证任务触发
4. **Approvals 测试**:
- 触发需要审批的 Hand
- 验证 Approvals 页面显示
- 批准/拒绝审批
### 5.2 自动化测试
```bash
# 运行相关测试
pnpm vitest run tests/desktop/handsPanel.test.tsx
pnpm vitest run tests/desktop/workflowList.test.tsx
pnpm vitest run tests/desktop/gatewayStore.test.ts
# 类型检查
pnpm tsc --noEmit
```
---
## 六、开发顺序 (根据用户确认)
**用户选择**:
- ✅ 优先实现 Hands 增强
- ✅ 需要完整实现 Scheduler 和 Approvals
**推荐开发顺序**:
| 顺序 | Phase | 工作量 | 说明 |
|------|-------|--------|------|
| 1 | Phase 1: HandsPanel 增强 | 2-3 天 | 最高优先级,核心功能 |
| 2 | Phase 4: ApprovalsPanel | 1 天 | Hand 执行需要审批流程 |
| 3 | Phase 2: WorkflowList 增强 | 2-3 天 | 完整工作流管理 |
| 4 | Phase 3: SchedulerPanel | 2 天 | 定时任务和事件触发器 |
| 5 | Phase 5: 导航重构 | 1-2 天 | 统一导航结构 |
| **总计** | - | **8-11 天** | - |
---
## 六-A、第一步实施细节: HandsPanel 增强
### 文件修改清单
1. **`desktop/src/components/HandsPanel.tsx`** (重写)
- 添加 HandCard 组件重构
- 添加状态徽章 (READY/SETUP NEEDED/RUNNING)
- 添加 Requirements 可视化
- 添加分类标签
- 添加工具/指标计数
2. **`desktop/src/components/HandDetailsModal.tsx`** (新建)
- Agent Config 显示 (Provider/Model)
- Requirements 列表
- Tools 列表
- Dashboard Metrics 列表
- Activate 按钮
3. **`desktop/src/store/gatewayStore.ts`** (扩展)
- 扩展 Hand 类型定义
- 添加 getHandDetails API
4. **`desktop/src/lib/gateway-client.ts`** (扩展)
- 添加 getHandDetails 方法
### UI 组件设计
```tsx
// HandStatusBadge 组件
type HandStatus = 'idle' | 'running' | 'needs_approval' | 'error' | 'unavailable' | 'setup_needed';
const STATUS_CONFIG: Record<HandStatus, { label: string; className: string }> = {
idle: { label: 'READY', className: 'bg-green-100 text-green-700' },
running: { label: 'RUNNING', className: 'bg-blue-100 text-blue-700 animate-pulse' },
needs_approval: { label: 'NEEDS APPROVAL', className: 'bg-yellow-100 text-yellow-700' },
error: { label: 'ERROR', className: 'bg-red-100 text-red-700' },
unavailable: { label: 'UNAVAILABLE', className: 'bg-gray-100 text-gray-500' },
setup_needed: { label: 'SETUP NEEDED', className: 'bg-orange-100 text-orange-700' },
};
// RequirementItem 组件
function RequirementItem({ description, met, details }: Requirement) {
return (
<div className={`flex items-start gap-2 text-sm ${met ? 'text-green-700' : 'text-red-600'}`}>
<span className="flex-shrink-0">{met ? '✓' : '✗'}</span>
<span>{description}</span>
{details && <span className="text-gray-400 text-xs">({details})</span>}
</div>
);
}
```
---
## 七、风险与缓解
| 风险 | 影响 | 缓解措施 |
|------|------|----------|
| OpenFang API 变更 | 高 | 使用实际 API 测试验证,保持与 OpenFang v0.4.0 兼容 |
| UI 复杂度 | 中 | 分阶段实现,先核心功能后高级功能 |
| 性能问题 | 低 | 使用虚拟列表处理大量数据 |
---
*计划创建时间: 2026-03-14*
*参考版本: OpenFang v0.4.0*

View File

@@ -1,386 +0,0 @@
# ZClaw: 从 OpenClaw 迁移到 OpenFang 可行性方案
> **规划日期**: 2026-03-13
> **目标**: 制定从 OpenClaw 到 OpenFang 的渐进式迁移策略,实现平稳过渡
---
## 一、背景与动机
### 1.1 当前架构 (OpenClaw)
```
┌─────────────────────────────────────────────────────────────────┐
│ ZClaw Desktop (当前) │
├─────────────────────────────────────────────────────────────────┤
│ React 19 UI → Zustand Store → GatewayClient → OpenClaw │
│ 技术栈: Tauri 2.0 + TypeScript + Node.js Gateway │
│ 内存: >1GB | 启动: 2-5s | 安装: 500MB │
└─────────────────────────────────────────────────────────────────┘
```
### 1.2 目标架构 (OpenFang)
```
┌─────────────────────────────────────────────────────────────────┐
│ ZClaw Desktop (OpenFang) │
├─────────────────────────────────────────────────────────────────┤
│ React 19 UI → Zustand Store → OpenFangClient → OpenFang │
│ 技术栈: Tauri 2.0 + TypeScript + Rust Gateway │
│ 内存: ~40MB | 启动: 180ms | 安装: 32MB │
└─────────────────────────────────────────────────────────────────┘
```
### 1.3 迁移动机
| 维度 | OpenClaw | OpenFang | 提升 |
|------|----------|----------|------|
| **启动速度** | 5.98s | 180ms | **33x 更快** |
| **内存占用** | 394MB | 40MB | **90% 更少** |
| **安装大小** | 500MB | 32MB | **94% 更小** |
| **安全防护** | 3 层 | 16 层 | **企业级安全** |
| **通道支持** | 20+ | 40+ | **覆盖更广** |
| **自主能力** | 无 | 7 Hands | **从被动到主动** |
---
## 二、核心差异分析
### 2.1 协议差异
| 方面 | OpenClaw | OpenFang |
|------|----------|----------|
| **WebSocket URL** | `ws://127.0.0.1:18789` | `ws://127.0.0.1:4200/ws` |
| **协议格式** | 自定义 JSON 帧 | 标准 JSON + gRPC |
| **认证方式** | Ed25519 设备签名 | Ed25519 + JWT |
### 2.2 配置差异
| 方面 | OpenClaw | OpenFang |
|------|----------|----------|
| **配置目录** | `~/.openclaw/` | `~/.openfang/` |
| **配置格式** | YAML/JSON | TOML |
| **插件系统** | TypeScript (`index.ts`) | SKILL.md + WASM |
### 2.3 API 差异
| 功能 | OpenClaw RPC | OpenFang API |
|------|-------------|--------------|
| 发送消息 | `agent` | `chat` / `/api/chat` |
| 列出 Agent | `zclaw.clones.list` | `GET /api/agents` |
| 获取配置 | `config.get` | `GET /api/config` |
| 触发技能 | 插件系统 | `skill_trigger` |
| Hand 自动化 | ❌ 无 | `hand_trigger` |
| Workflow | ❌ 基础 | `workflow_execute` |
---
## 三、迁移策略:渐进式双轨
### 3.1 策略原则
1. **双版本并行**: 保持 OpenClaw 可用,同时开发 OpenFang
2. **适配层抽象**: 通过接口隔离后端差异
3. **功能对等优先**: 先保证核心功能,再添加新特性
4. **灰度发布**: Beta 测试验证后全面切换
### 3.2 迁移阶段
```
Phase 1 (2周): 基础设施 ──────────────────────────────────────────►
Phase 2 (2周): 客户端实现 ────────────────────────────────────────►
Phase 3 (2周): 状态迁移 ──────────────────────────────────────────►
Phase 4 (3周): 插件迁移 ──────────────────────────────────────────►
Phase 5 (2周): Tauri 后端 ────────────────────────────────────────►
Phase 6 (3周): UI 增强 ───────────────────────────────────────────►
Phase 7 (2周): 测试验证 ──────────────────────────────────────────►
────────────────────────────────────────────────────────────────────
总工期: 16 周 (约 4 个月)
```
---
## 四、详细实施计划
### Phase 1: 基础设施 (Week 1-2)
**目标**: 建立迁移基础架构
**关键任务**:
1. 创建 `GatewayBackend` 接口抽象
2. 创建 `OpenFangClient` 骨架
3. 配置双后端切换机制
4. 设置 OpenFang 开发环境
**交付物**:
- `desktop/src/lib/types/gateway-backend.ts` - 接口定义
- `desktop/src/lib/openfang-client.ts` - 客户端骨架
- `desktop/src/lib/backend-factory.ts` - 后端工厂
### Phase 2: 客户端实现 (Week 3-4)
**目标**: 完整实现 OpenFang 客户端
**关键文件**: [gateway-client.ts](desktop/src/lib/gateway-client.ts)
**修改内容**:
```typescript
// 1. 抽取接口
interface GatewayBackend {
connect(): Promise<void>;
disconnect(): void;
chat(message: string, opts?: ChatOptions): Promise<{runId: string}>;
onStream(callback: StreamCallback): () => void;
// ... 其他方法
}
// 2. OpenClaw 实现 (现有代码重构)
class OpenClawBackend implements GatewayBackend { ... }
// 3. OpenFang 实现 (新建)
class OpenFangBackend implements GatewayBackend {
private ws: WebSocket;
private url = 'ws://127.0.0.1:4200/ws';
async connect(): Promise<void> {
// OpenFang 认证协议
}
async chat(message: string, opts?: ChatOptions): Promise<{runId: string}> {
// OpenFang chat 格式
}
}
```
### Phase 3: 状态迁移 (Week 5-6)
**目标**: 更新状态管理层支持双后端
**关键文件**: [gatewayStore.ts](desktop/src/store/gatewayStore.ts)
**修改内容**:
```typescript
interface GatewayStore {
// 新增
backendType: 'openclaw' | 'openfang';
switchBackend(type: 'openclaw' | 'openfang'): void;
// 修改 connect 方法
connect: async (url?, token?) => {
const backend = getBackendFactory().create(get().backendType);
await backend.connect(url, token);
}
}
```
### Phase 4: 插件迁移 (Week 7-9)
**目标**: 迁移现有插件到 OpenFang 格式
| 插件 | 当前格式 | 目标格式 | 复杂度 |
|------|----------|----------|--------|
| `zclaw-chinese-models` | TypeScript | TOML 配置 | 中 |
| `zclaw-feishu` | TypeScript | Rust/WASM | 高 |
| `zclaw-ui` | TypeScript RPC | REST API | 高 |
**迁移方案**:
```
plugins/
├── zclaw-chinese-models/
│ ├── openclaw.plugin.json → 删除
│ └── index.ts → 转换为 providers.toml
├── zclaw-feishu/
│ └── index.ts → 迁移到 OpenFang channels
└── zclaw-ui/
└── index.ts → 拆分为 REST 端点
```
### Phase 5: Tauri 后端 (Week 10-11)
**目标**: 更新 Rust 后端支持 OpenFang
**关键文件**: [lib.rs](desktop/src-tauri/src/lib.rs)
**修改内容**:
```rust
// 新增 OpenFang 命令
#[tauri::command]
async fn openfang_status() -> Result<OpenFangStatus, String> { ... }
#[tauri::command]
async fn openfang_start() -> Result<(), String> { ... }
#[tauri::command]
async fn openfang_stop() -> Result<(), String> { ... }
// 新增配置迁移命令
#[tauri::command]
async fn migrate_to_openfang() -> Result<MigrationResult, String> { ... }
```
### Phase 6: UI 增强 (Week 12-14)
**目标**: 添加 OpenFang 特有的 UI 功能
**新增组件**:
1. `HandsPanel.tsx` - Hands 管理界面
2. `WorkflowEditor.tsx` - 工作流编辑器
3. `TriggerManager.tsx` - 触发器管理
4. `AuditLogs.tsx` - 审计日志查看
**修改组件**:
1. `SettingsLayout.tsx` - 添加后端切换选项
2. `General.tsx` - 添加 OpenFang 配置项
### Phase 7: 测试验证 (Week 15-16)
**目标**: 全面测试和验证
**测试范围**:
- 单元测试: 新客户端、适配层
- 集成测试: 端到端消息流
- 性能测试: 启动时间、内存占用
- 迁移测试: 配置迁移正确性
---
## 五、风险评估与缓解
### 5.1 技术风险
| 风险 | 级别 | 缓解措施 |
|------|------|----------|
| 协议不兼容 | 高 | 创建适配层,保持双后端 |
| 插件迁移复杂 | 高 | 分阶段迁移,保持 TypeScript 桥接 |
| OpenFang 不成熟 | 中 | 持续关注上游,建立社区联系 |
| 配置格式差异 | 中 | 构建自动迁移工具 |
### 5.2 运营风险
| 风险 | 级别 | 缓解措施 |
|------|------|----------|
| 用户困惑 | 中 | 清晰文档,渐进发布 |
| 数据丢失 | 高 | 自动备份,非破坏性迁移 |
| 支持负担 | 中 | FAQ故障排除指南 |
### 5.3 回滚策略
```typescript
// 环境变量切换
const USE_OPENFANG = process.env.ZCLAW_USE_OPENFANG === 'true';
// localStorage 切换
const backendType = localStorage.getItem('zclaw-backend') || 'openclaw';
// 一键回滚
function rollbackToOpenClaw() {
localStorage.setItem('zclaw-backend', 'openclaw');
window.location.reload();
}
```
---
## 六、验证方案
### 6.1 功能验证清单
**核心功能**:
- [ ] WebSocket 连接和认证
- [ ] 消息发送和流式接收
- [ ] Agent/Clone CRUD 操作
- [ ] 频道管理 (飞书)
- [ ] 技能加载和执行
- [ ] 使用统计
- [ ] 配置管理
**OpenFang 新特性**:
- [ ] Hand 触发 (Clip, Lead, Researcher 等)
- [ ] Workflow 执行
- [ ] 16 层安全验证
- [ ] 审计日志访问
### 6.2 性能基准
| 指标 | OpenClaw 基线 | OpenFang 目标 |
|------|---------------|---------------|
| 冷启动 | 5.98s | < 500ms |
| 空闲内存 | 394MB | < 100MB |
| 聊天延迟 | 100ms | < 50ms |
| 安装大小 | 500MB | < 100MB |
---
## 七、关键文件清单
| 文件 | 修改类型 | 说明 |
|------|----------|------|
| [gateway-client.ts](desktop/src/lib/gateway-client.ts) | 重构 | 抽取接口创建 OpenFang 实现 |
| [gatewayStore.ts](desktop/src/store/gatewayStore.ts) | 修改 | 添加后端切换逻辑 |
| [chatStore.ts](desktop/src/store/chatStore.ts) | 修改 | 适配新事件格式 |
| [lib.rs](desktop/src-tauri/src/lib.rs) | 扩展 | 添加 OpenFang 管理命令 |
| [zclaw-ui/index.ts](plugins/zclaw-ui/index.ts) | 迁移 | 转换为 REST API |
| [zclaw-chinese-models/index.ts](plugins/zclaw-chinese-models/index.ts) | 迁移 | 转换为 TOML 配置 |
| [zclaw-feishu/index.ts](plugins/zclaw-feishu/index.ts) | 迁移 | 使用 OpenFang channel |
---
## 八、时间线总结
| 阶段 | 周期 | 开始 | 结束 | 关键交付物 |
|------|------|------|------|------------|
| Phase 1 | 2周 | Week 1 | Week 2 | OpenFangClient 骨架 |
| Phase 2 | 2周 | Week 3 | Week 4 | 完整客户端 + 流式处理 |
| Phase 3 | 2周 | Week 5 | Week 6 | 更新后的 stores |
| Phase 4 | 3周 | Week 7 | Week 9 | 迁移后的插件 |
| Phase 5 | 2周 | Week 10 | Week 11 | Rust OpenFang 支持 |
| Phase 6 | 3周 | Week 12 | Week 14 | Hands/Workflow UI |
| Phase 7 | 2周 | Week 15 | Week 16 | 测试套件验证报告 |
**总工期**: 16 ( 4 个月)
---
## 九、结论与建议
### 9.1 核心价值
```
┌─────────────────────────────────────────────────────────────────┐
│ │
│ 🚀 性能33x 启动速度 + 90% 内存节省 │
│ │
│ 🔒 安全16 层纵深防御 + 金融级合规 │
│ │
│ 🤖 智能Hands 自主系统 + Workflow 引擎 │
│ │
│ 📈 商业:企业市场拓展 + 定价提升空间 │
│ │
│ ⚠️ 成本16 周 (4个月) 迁移周期 │
│ │
└─────────────────────────────────────────────────────────────────┘
```
### 9.2 决策建议
| 目标 | 建议 |
|------|------|
| 追求企业市场 | **强烈建议迁移** |
| 追求差异化竞争 | **建议迁移** |
| 目标是内容创作者/销售 | **强烈建议迁移** |
| 资源有限 | 渐进评估 |
| 追求快速迭代 | 保持 OpenClaw关注 OpenFang |
### 9.3 下一步行动
1. **立即**: 确认迁移决策分配资源
2. **Week 1**: 创建 `GatewayBackend` 接口
3. **Week 2**: 搭建 OpenFang 开发环境
4. **Week 3-4**: 实现 `OpenFangClient`
---
*规划日期: 2026-03-13*
*版本: v1.0*

View File

@@ -1,420 +0,0 @@
# ZCLAW 新会话提示词后续工作计划
## 一、目标
围绕 ZCLAW 的“新会话提示词”能力,完成一条从 **真实 Agent 配置****真实会话初始化行为** 的可交付链路。
这项能力的目标不是增加一个前端文本框,而是让用户可以:
- 为当前 Agent 设置默认的新会话提示词
- 在开启某个新会话时临时覆盖这段提示词
- 让提示词真实影响本次会话第一轮 Agent 行为
- 让该能力在快速配置、右侧 Agent 面板、聊天区之间语义一致
---
## 二、当前已确认基础
以下基础能力已经打通,可作为本轮工作的前提:
- Gateway 连接稳定可用
- token 注入、自动连接、Control UI 握手已修好
- `zclaw-ui` 插件已加载
- `zclaw.clones.list``zclaw.plugins.status` 可用
- Agent 创建、右侧 Agent 面板编辑、保存回刷已验证通过
- 快速配置应视为创建/更新 OpenClaw Agent
- 右侧 Agent 面板已经是当前 Agent 配置的真实编辑入口
这意味着“新会话提示词”应该优先挂在 **Agent Profile 真实配置链路** 上,而不是再创建一套独立的本地状态。
---
## 三、问题定义
当前“新对话”链路还存在几个明显缺口:
### 3.1 会话初始化仍是本地 UI 行为
现状:
- `chatStore.newConversation()` 只清空本地消息与 `sessionKey`
- 首次发送时才临时生成 `sessionKey`
- 当前没有“会话初始化参数”的明确模型
影响:
- 新会话无法承载独立初始化上下文
- 会话开场行为不可控、不可审计
### 3.2 Agent 配置与新会话行为未打通
现状:
- Agent 已有真实配置入口
- 但聊天区不会消费“新会话默认提示词”这一能力
影响:
- Agent 身份和会话起始行为割裂
- 用户改了 Agent不一定影响新会话
### 3.3 当前没有原生会话初始化协议
现状:
- 当前 Gateway `agent` 请求只传 `message / sessionKey / model`
- 尚未形成 `sessionInit``agentId``conversationContext` 等结构化初始化协议
影响:
- 若不做桥接,“新会话提示词”很难真实生效
---
## 四、设计原则
### 4.1 必须改变真实运行行为
验收标准不是“页面上能输入”,而是:
- 第一条发给 Gateway 的真实消息已经体现新会话提示词
- 不同会话可以有不同初始化上下文
- 会话恢复后能够看出本会话使用过什么提示词
### 4.2 必须依附真实 Agent 配置链路
能力入口必须统一在以下两处:
- 快速配置创建 Agent
- 右侧 Agent 面板编辑当前 Agent
不新增与 Agent 平行、脱节的新设置体系。
### 4.3 先做最小真实闭环,再继续原生化
本轮优先实现:
- Agent 级默认 `newSessionPrompt`
- 会话级 `sessionPromptDraft`
- 首轮消息注入
后续再根据 Gateway / OpenClaw 演进升级为结构化原生协议。
---
## 五、目标能力定义
### 5.1 Agent 级默认提示词
语义:
- 某个 Agent 在每次开始新会话时默认携带的启动上下文
- 属于 Agent Profile 的一部分
- 可以由快速配置或右侧 Agent 面板编辑
建议字段:
- `newSessionPrompt?: string`
### 5.2 会话级临时覆盖
语义:
- 仅对本次新会话生效
- 发出第一条用户消息前可编辑
- 发出后固化到会话元数据中,不应在后续回合反复注入
建议字段:
- `sessionPromptDraft: string`
- `conversation.sessionPrompt?: string | null`
### 5.3 首轮运行时注入
语义:
- 前端保留原始用户输入展示
- 发送给 Gateway 的第一条消息在内部包装为“新会话提示词 + 原始用户问题”
- 从而让提示词立即影响真实模型行为
---
## 六、实施阶段拆分
## Phase 1数据模型与 RPC 链路补齐
### 目标
让“新会话提示词”成为真实 Agent 数据结构的一部分。
### 涉及位置
- `plugins/zclaw-ui/index.ts`
- `desktop/src/store/gatewayStore.ts`
- `desktop/src/store/chatStore.ts`
- `desktop/src/components/CloneManager.tsx`
- `desktop/src/components/RightPanel.tsx`
### 具体任务
- 插件层 `CloneConfig` 增加 `newSessionPrompt`
- `zclaw.clones.create/update/list` 全链路透传该字段
- 前端 `Clone`、快速配置草稿、右侧面板草稿模型补齐字段
- 保证创建后、编辑后、刷新后都能回刷正确数据
### 交付物
- Agent Profile 可持久化 `newSessionPrompt`
- UI 能读取并展示该字段
### 验收标准
- 创建 Agent 时可设置默认新会话提示词
- 右侧 Agent 面板可编辑并保存该字段
- 重新连接或刷新后字段仍存在
---
## Phase 2聊天会话模型扩展
### 目标
为“新会话提示词”建立真正的会话级承载结构。
### 具体任务
- `chatStore` 增加 `sessionPromptDraft`
- `Conversation` 增加 `sessionPrompt``agentId`
- `newConversation()` 时重置当前会话的提示词草稿
- 当切换 Agent 且当前尚未开始聊天时,提示词草稿应回填为当前 Agent 默认值
- 切换到历史会话时,恢复该会话使用过的 `sessionPrompt`
### 交付物
- 会话层面拥有独立的提示词状态
- 会话与 Agent 的关系更清晰
### 验收标准
- 新会话默认读取当前 Agent 的默认提示词
- 修改草稿只影响当前新会话,不污染其他历史会话
- 切回历史会话时能恢复对应提示词信息
---
## Phase 3首轮消息注入打通真实运行行为
### 目标
让“新会话提示词”真正影响 Gateway 收到的第一条消息。
### 具体任务
-`chatStore.sendMessage()` 判断当前是否为该会话首轮用户消息
- 若有有效 `sessionPromptDraft`,则构造包装后的发送内容
- UI 中仍展示用户原始输入,不暴露包装结构
- 首轮发出后,将实际使用过的提示词固化到当前 `Conversation`
- 后续同一会话继续发送消息时不重复注入
### 建议包装格式
```text
[ZCLAW_NEW_SESSION_PROMPT]
<session prompt>
[/ZCLAW_NEW_SESSION_PROMPT]
[USER_MESSAGE]
<original user message>
[/USER_MESSAGE]
```
### 交付物
- 新会话提示词真正进入第一轮 Gateway 请求
- 该能力不再是展示层占位
### 验收标准
- 第一轮消息有提示词时,模型行为明显受影响
- 第二轮起不再重复注入
- 无提示词时发送链路与当前一致
---
## Phase 4交互与可见性优化
### 目标
让用户知道“当前会话将以什么上下文启动”,同时避免界面复杂度失控。
### 具体任务
- 在聊天区空态增加“新会话提示词”输入区
- 提供简洁说明文案,明确这是“仅本次会话”的覆盖入口
- 在右侧 Agent 面板非编辑态显示默认新会话提示词摘要
- 在历史会话列表或会话详情中,保留轻量提示,帮助用户理解该会话的启动上下文
### 交付物
- 新会话前可见、可改、可理解
- Agent 默认值与会话覆盖值关系明确
### 验收标准
- 用户能区分“Agent 默认值”和“当前会话覆盖值”
- 用户不会误以为这是长期人格或全局系统提示词
---
## Phase 5质量保障与回归验证
### 目标
确保能力上线后不会破坏现有已打通链路。
### 测试范围
- Agent 创建后默认提示词可保存
- 右侧 Agent 面板编辑提示词可回刷
- 新会话读取默认值
- 新会话覆盖值只作用于当前会话
- 首轮消息注入只发生一次
- 切换历史会话后元数据恢复正确
- 无提示词情况下原有发送链路不回归
### 建议验证方式
- Store 层单元测试
- 关键组件交互测试
- 手工联调验证 Gateway 请求行为
### 交付物
- 至少覆盖核心 store 行为的测试
- 一份人工回归清单
### 验收标准
- 核心交互不回归
- 会话状态与 Agent 状态一致性可验证
---
## 七、推荐执行顺序
建议按以下顺序推进,避免前后反复返工:
### 第一步
先做 **Phase 1**
原因:
- 没有真实字段,就谈不上后续真实会话能力
- 这一步风险最低,收益明确
### 第二步
**Phase 2**
原因:
- 会话级草稿与历史恢复能力是首轮注入的前提
### 第三步
**Phase 3**
原因:
- 这是从“有配置”到“真生效”的关键跃迁
- 也是这轮工作的核心里程碑
### 第四步
**Phase 4 + Phase 5**
原因:
- 在核心链路稳定后,再做可见性和质量封口最合适
---
## 八、本轮建议的最小可交付版本
如果本轮只做一个最小但高价值版本,建议交付以下内容:
- 插件与前端数据模型支持 `newSessionPrompt`
- 快速配置与右侧 Agent 面板都可编辑该字段
- 聊天区空态可查看/修改当前新会话提示词
- 首轮消息自动注入该提示词
- 会话中记录本次实际使用的提示词
这版已经满足:
- 有真实配置入口
- 有真实运行时行为
- 有会话级语义
- 能被用户实际使用
---
## 九、主要风险与处理策略
### 风险 1当前 selected Agent 还未完全映射到 OpenClaw runtime agent
影响:
- 即使 Agent Profile 已切换,底层仍可能没有原生 agent routing
处理:
- 本轮先用“首轮消息注入”保证真实行为变化
- 后续把 `agentId` 传输与 runtime routing 作为独立里程碑推进
### 风险 2提示词注入格式可能影响回答质量
影响:
- 包装格式不佳时,可能让模型输出不稳定
处理:
- 采用清晰、边界明确的包裹格式
- 在真实模型上做几组样例测试
### 风险 3会话切换与持久化逻辑容易变脆
影响:
- 草稿、历史会话、当前会话三者状态可能串扰
处理:
- 优先把 store 状态边界设计清楚
- 先覆盖核心状态迁移测试,再做 UI 微调
---
## 十、完成定义
当以下条件同时满足时,可视为“新会话提示词”能力第一阶段完成:
- Agent 默认新会话提示词可创建、编辑、保存、回刷
- 新会话开始前用户可临时覆盖该提示词
- 首轮真实发送到 Gateway 的消息中包含该提示词上下文
- 同一会话后续消息不重复注入
- 历史会话可以恢复其实际使用过的提示词信息
- 快速配置、右侧 Agent 面板、聊天区三处语义一致
---
## 十一、下一步建议
在本计划落地后,建议立即开始:
- **P1先补数据模型与插件透传**
- **P2再补 chatStore 的会话级状态模型**
- **P3最后接入首轮消息注入并做联调验证**
这会以最小改动建立一条真正可用的闭环,也是当前最符合 ZCLAW 产品化推进方向的高杠杆路径。

View File

@@ -1,231 +0,0 @@
# ZClaw 改进方案:从"前端 UI 演示"升级为"真正的 OpenClaw Runtime 控制界面"
**日期**: 2026-03-12
**状态**: 规划中
---
## 背景分析
### 当前状态
经过对代码库的深入分析,发现以下关键差距:
#### 1. 分身与 Agent 断层
- **现状**: 分身存储在 `zclaw-data.json` (ZCLAW 自定义格式)
- **问题**: 不映射到 OpenClaw 原生 `agents.list` 配置
- **影响**: 聊天时不所有分身共用 `main` Agent
- **表现**: Bootstrap 文件生成了但可能未被 Agent 运行时使用
**关键代码位置**:
- `desktop/src/components/CloneManager.tsx`: 分身 CRUD 界面
- `desktop/src/store/chatStore.ts`: `currentAgent` 只存前端状态
- `plugins/zclaw-ui/index.ts`: 分身存储在 `zclaw-data.json`
#### 2. 设置页是"假状态"
- **现状**: 大部分设置只存 localStorage
- **问题**: 没有调用 OpenClaw 的 `config.get/config.patch/config.apply`
- **影响**: 用户改了设置而 OpenClaw 运行时行为不变
**关键代码位置**:
- `desktop/src/components/Settings/*.tsx`: 所有设置页面
- `desktop/src/store/chatStore.ts`: `currentModel` 只存前端状态
- `desktop/src/lib/gateway-client.ts`: 缺少 `config.*` RPC 方法
#### 3. 右侧面板数据不真实
- **现状**: 部分数据是硬编码默认值
- **问题**: 没有显示真实 Agent 的运行时状态
- **影响**: 用户看到的是演示数据,- **表现**: Bootstrap 文件生成了但可能未被 Agent 运行时使用
---
## P0: 最小可行改进 - 让分身真正工作
### 目标
让分身系统真正映射到 OpenClaw Agent 实例,实现分身隔离(独立 Agent 会话)。
### 关键任务
#### 1. 实现 Agent 同步机制
-`plugins/zclaw-ui/index.ts` 中:
- 添加 `zclaw.agents.sync` RPC 方法
- 同步 `zclaw-data.json` 的分身到 `agents.list`
- 为每个分身创建独立 `agentDir`
-`desktop/src/lib/gateway-client.ts` 中:
- 添加 `agents.list` RPC 方法封装
- 添加 `agent.set` RPC 方法封装
#### 2. 修改聊天逻辑
-`desktop/src/store/chatStore.ts` 中:
- 添加 `currentAgentId` 字段
- 修改 `sendMessage` 传递 `agentId`
-`desktop/src/components/ChatArea.tsx` 中:
- 聊天时显示当前分身信息
#### 3. Agent 启动流程
- 创建分身时:
1. 生成 Bootstrap 文件
2. 同步到 `agents.list`
3. 重启 Agent 进程(如果需要)
- 切换分身时:
1. 加载对应 Agent 的上下文
2. 切换 `agentId`
### 技术挑战
- **OpenClaw Agent 进程管理**: 隐式依赖 Gateway 的 Agent 启动机制
- **会话隔离**: 需要验证 OpenClaw 是否支持 `agentId` 参数
- **配置同步时机**: 何时同步分身配置到 OpenClaw
- **错误处理**: Agent 启动失败时的回退策略
### 验收标准
- [ ] 创建分身后能在 OpenClaw 的 `agents.list` 中看到
- [ ] 切换分身后聊天时传递正确的 `agentId`
- [ ] 不同分身的会话完全隔离
- [ ] Bootstrap 文件被 Agent 正确加载
- [ ] 分身配置修改后 Agent 行为相应变化
---
## P1: 设置页 Runtime 化
### 目标
让设置页真正修改 OpenClaw Runtime 配置。
### 关键任务
#### 1. GatewayClient 扩展
`desktop/src/lib/gateway-client.ts` 中添加:
```typescript
async getConfig(path?: string): Promise<any>
async patchConfig(path: string, value: any): Promise<void>
async applyConfig(): Promise<void>
```
#### 2. 设置页改造
**模型与 API**:
- 模型选择调用 `patchConfig('agents.defaults.model', model)`
- 显示当前模型从 `getConfig('agents.defaults.model')` 获取
**MCP 服务**:
- 读取: `getConfig('mcp')`
- 修改: `patchConfig('mcp.servers.*')`
**技能**:
- 读取: `getConfig('skills')`
- 修改: `patchConfig('skills.load.extraDirs')`
**IM 频道**:
- 读取: `getConfig('channels')`
- 修改: `patchConfig('channels.*')`
**工作区**:
- 读取: `getConfig('agents.defaults.workspace')`
- 修改: `patchConfig('agents.defaults.workspace')`
### 技术挑战
- **配置路径**: OpenClaw 配置是嵌套结构,需要正确处理路径
- **配置验证**: 修改前验证配置有效性
- **错误恢复**: 配置修改失败时的回滚
- **UI 反馈**: 配置修改时的加载状态
- **配置缓存**: 避免频繁读取配置
### 验收标准
- [ ] 模型选择后聊天时使用新模型
- [ ] MCP 开关后工具可用性变化
- [ ] 技能添加后 Agent 可调用
- [ ] IM 频道配置后能收发消息
- [ ] 工作区修改后文件访问范围变化
- [ ] 配置修改后重启 Gateway 生效
---
## P2: 完整的 Agent 管理系统
### 目标
实现完整的 Agent 生命周期管理。
### 关键任务
#### 1. Agent 状态管理
`desktop/src/store/chatStore.ts` 中添加
```typescript
interface AgentState {
id: string;
status: 'idle' | 'running' | 'error';
lastActive: Date;
sessionCount: number;
currentModel: string;
}
```
#### 2. Agent 监控
`plugins/zclaw-ui/index.ts` 中添加
```typescript
api.registerGatewayMethod('zclaw.agents.status', ({ respond }) => {
// 返回所有 Agent 的运行时状态
});
```
#### 3. 右侧面板增强
`desktop/src/components/RightPanel.tsx`
- 显示真实 Agent 状态
- 显示运行时信息(当前任务、 使用的工具等)
- 显示会话历史
### 技术挑战
- **状态同步**: 客户端状态与 Gateway 状态同步
- **性能**: 大量 Agent 时的性能
- **错误处理**: Agent 状态异常时的 UI 反馈
- **实时更新**: 状态变化时的实时推送
### 验收标准
- [ ] Agent 状态实时显示
- [ ] 运行时信息准确
- [ ] 会话历史可查
- [ ] 错误状态有明确提示
- [ ] 性能满足要求(100 个 Agent)
---
## P3: 产品化封装
### 目标
提供完整的桌面应用体验。
### 关键任务
#### 1. Tauri Sidecar 管理
`desktop/src-tauri/src/gateway.rs` 中:
- 管理 Gateway 子进程生命周期
- 自动重启和错误恢复
- 配置管理和持久化
#### 2. 首次启动体验
- 欢迎向导
- Gateway 连接配置
- 默认 Agent 创建
- 工作目录选择
#### 3. 错误诊断
- 连接问题诊断
- 配置错误修复建议
- 日志查看工具
### 技术挑战
- **进程管理**: 跨平台进程管理
- **权限**: 文件系统访问权限
- **更新**: 应用更新时的状态保持
- **用户体验**: 错误时的用户引导
- **文档**: 用户文档和帮助
### 验收标准
- [ ] Gateway 自动启动
- [ ] 首次启动流程完整
- [ ] 错误有明确指引
- [ ] 配置持久化
- [ ] 应用更新无状态丢失
- [ ] 用户文档完整

View File

@@ -1,343 +0,0 @@
# ZClaw 项目深度分析与改进计划
## 一、现状分析
### 1.1 核心发现
基于 `docs/openclaw-deep-dive.md` 的目标与实际代码的对比:
| 模块 | 目标状态 | 实际状态 | 差距程度 |
|------|----------|----------|----------|
| **Gateway 连接** | 设备认证 + Challenge 签名 | ✅ 完整实现 | 无差距 |
| **分身系统** | 映射到 OpenClaw `agents.list` | ⚠️ 独立存储在 `zclaw-data.json` | **严重** |
| **设置页** | OpenClaw Runtime 配置面板 | ⚠️ 大部分是前端本地状态 | **严重** |
| **右侧面板** | 真实 Agent 身份与状态 | ⚠️ 混合真实数据与硬编码值 | **中等** |
### 1.2 关键差距详解
#### 差距 1分身与 Agent 断层(最严重)
```
当前架构:
┌─────────────────────────────────────────────────────────────┐
│ ZClaw 分身系统 (zclaw-data.json) │
│ clone_1: { name: "程序员", workspaceDir: "...", ... } │
│ clone_2: { name: "设计师", workspaceDir: "...", ... } │
└────────────────────────┬────────────────────────────────────┘
│ ❌ 无同步
┌─────────────────────────────────────────────────────────────┐
│ OpenClaw agents.list (openclaw.json) │
│ 只有: [{ id: "main", groupChat: {...} }] │
└─────────────────────────────────────────────────────────────┘
```
**后果**
- 所有分身实际共用同一个 `main` Agent
- 聊天时不传递 `agentId`OpenClaw 不知道当前是哪个分身
- Bootstrap 文件IDENTITY.md, SOUL.md 等)生成了但未被运行时使用
#### 差距 2设置页是"假状态"
| 设置页 | 当前实现 | 应该实现 |
|--------|----------|----------|
| 模型选择 | 存在 `chatStore.currentModel`(前端状态) | 调用 `config.patch` 修改 OpenClaw 配置 |
| MCP 服务 | 存 `quickConfig`,部分同步到 Gateway | 管理 `plugins.load.paths` |
| 技能目录 | 存 `quickConfig` | 管理 `skills.load.extraDirs` |
| IM 频道 | 存 `quickConfig`,只显示状态 | 管理 `channels.*` 配置 |
| 工作区 | 存 `quickConfig` | 管理 `agents.defaults.workspace` |
| 隐私 | 存 `quickConfig` | 管理 telemetry/优化计划 |
**缺失的 RPC 方法**
- `config.get` - 读取 OpenClaw 配置
- `config.patch` - 修改配置
- `config.apply` - 热更新配置
#### 差距 3右侧面板数据不真实
```typescript
// 硬编码的默认值RightPanel.tsx
const credits = 2268; // 完全假数据
const defaultUserName = '用户7141'; // 假用户名
```
---
## 二、根因分析
### 2.1 架构层面的偏差
**文档期望**
> ZClaw 应该是 OpenClaw Runtime 的控制界面
**实际实现**
> ZClaw 是一个有自己数据模型的前端应用,与 OpenClaw 是松耦合
### 2.2 数据模型的分裂
```
OpenClaw 数据模型:
openclaw.json → agents.list → Agent workspace → Bootstrap files
ZClaw 数据模型:
zclaw-data.json → clones[] → (独立的) workspace 路径
```
两套数据模型没有桥接,导致:
1. 分身不能路由到正确的 Agent
2. 设置不能影响 OpenClaw 行为
3. Bootstrap 文件与运行时脱节
---
## 三、头脑风暴:改进方案
### 3.1 方案 A完全对齐 OpenClaw推荐
**核心思路**:让 ZClaw 分身直接映射到 OpenClaw Agent
```
改进后架构:
┌─────────────────────────────────────────────────────────────┐
│ ZClaw 分身 = OpenClaw Agent │
│ │
│ clone_1 ↔ agents.list[0] (id: "programmer") │
│ clone_2 ↔ agents.list[1] (id: "designer") │
│ │
│ 分身 CRUD → 同步修改 agents.list │
│ 聊天时 → 传递 agentId 到 Gateway │
└─────────────────────────────────────────────────────────────┘
```
**优点**
- 符合 `openclaw-deep-dive.md` 的设计哲学
- 分身真正有独立人格、记忆、工具权限
- 设置页可以直接操作 OpenClaw 配置
**缺点**
- 改动较大,需要修改多个模块
- 需要处理数据迁移
### 3.2 方案 B保持独立增强桥接
**核心思路**:保持 `zclaw-data.json`,但增加同步逻辑
```
改进后架构:
┌─────────────────────────────────────────────────────────────┐
│ ZClaw 分身系统 (主) │
│ zclaw-data.json → clones[] │
│ │ │
│ ▼ (单向同步) │
│ openclaw.json → agents.list (从分身生成) │
└─────────────────────────────────────────────────────────────┘
```
**优点**
- 改动较小
- 保持现有分身管理逻辑
**缺点**
- 数据冗余,需要维护同步
- 不符合 OpenClaw 的设计哲学
### 3.3 方案 C混合模式
**核心思路**
- 简单分身:共用 `main` Agent通过 Bootstrap 文件区分
- 高级分身:映射到独立 OpenClaw Agent
---
## 四、推荐实施路线(方案 A
### P0让分身真正工作最小可行
**目标**:创建分身时同步到 OpenClaw `agents.list`,聊天时传递 `agentId`
**关键修改**
1. **`plugins/zclaw-ui/index.ts`**
- `createClone` 时调用 OpenClaw API 添加到 `agents.list`
- `deleteClone` 时从 `agents.list` 移除
- 新增 `zclaw.agents.sync` 方法
2. **`desktop/src/lib/gateway-client.ts`**
- `chat()` 方法增加 `agentId` 参数
```typescript
async chat(message: string, opts?: { agentId?: string; sessionKey?: string }): Promise<...>
```
3. **`desktop/src/store/chatStore.ts`**
- `sendMessage` 时传递 `currentAgent.id` 作为 `agentId`
4. **新增 Gateway RPC**
- `zclaw.config.get` - 读取 OpenClaw 配置
- `zclaw.config.patch` - 修改配置
**验收标准**
- [ ] 创建分身后,`openclaw.json` 的 `agents.list` 包含新 Agent
- [ ] 切换分身后,聊天请求携带正确的 `agentId`
- [ ] 每个分身有独立的对话上下文
### P1设置页 Runtime 化
**目标**:设置修改直接影响 OpenClaw Runtime
**关键修改**
1. **`desktop/src/lib/gateway-client.ts`**
- 实现 `configGet()`、`configPatch()`、`configApply()` 方法
2. **各设置页改造**
- **模型与 API**:调用 `config.patch` 修改 `agents.defaults.model`
- **MCP 服务**:管理 `plugins.load.paths`
- **技能目录**:管理 `skills.load.extraDirs`
- **工作区**:管理 `agents.defaults.workspace`
- **隐私**:管理 telemetry 相关配置
3. **UI 反馈**
- 显示配置保存状态
- 配置变更后显示"需要重启"提示(如需要)
**验收标准**
- [ ] 模型选择后,`openclaw.json` 的 `agents.defaults.model` 更新
- [ ] 添加技能目录后,`skills.load.extraDirs` 更新
- [ ] Gateway 重启后配置生效
### P2完整的 Agent 管理系统
**目标**:分身管理 = Agent 全生命周期管理
**功能扩展**
1. 分身绑定渠道(飞书账号、微信群等)
2. 分身 Heartbeat 配置
3. 分身工具权限/沙箱配置
4. 分身间路由规则
**UI 改进**
- 右侧面板显示真实 Agent 状态(非硬编码)
- 分身详情页增加完整配置选项
### P3产品化封装
**目标**:开箱即用的桌面体验
**功能**
1. Tauri sidecar 管理 Gateway 进程
2. 首次安装配置向导
3. 错误诊断与自动修复
4. 一键更新
---
## 五、关键文件清单
| 文件 | 修改内容 |
|------|----------|
| `plugins/zclaw-ui/index.ts` | 分身 CRUD 同步到 agents.list |
| `desktop/src/lib/gateway-client.ts` | 增加 agentId 参数、config RPC |
| `desktop/src/store/chatStore.ts` | sendMessage 传递 agentId |
| `desktop/src/store/gatewayStore.ts` | 管理 Agent 配置状态 |
| `desktop/src/components/CloneManager.tsx` | 显示同步状态 |
| `desktop/src/components/RightPanel.tsx` | 显示真实 Agent 数据 |
| `desktop/src/components/Settings/*.tsx` | 改造为 Runtime 配置面板 |
| `config/openclaw.default.json` | 更新默认 Agent 模板 |
---
## 六、风险与缓解
| 风险 | 缓解措施 |
|------|----------|
| 数据迁移复杂 | 提供迁移脚本,保留 `zclaw-data.json` 作为备份 |
| OpenClaw 版本兼容 | 检测 OpenClaw 版本,低版本降级到兼容模式 |
| 破坏现有功能 | 灰度发布,支持回滚 |
| 性能下降 | 懒加载 Agent 配置,缓存 RPC 结果 |
---
## 七、确认的方案
**选择:方案 A - 完全对齐 OpenClaw**
理由:
1. 符合 `openclaw-deep-dive.md` 的设计哲学
2. 分身真正有独立人格、记忆、工具权限
3. 设置页可以直接操作 OpenClaw 配置
4. 长期维护成本最低
---
## 八、下一步行动P0 详细任务)
### Task 1: 修改 `zclaw-ui` 插件 - 分身同步到 agents.list
**文件**: `plugins/zclaw-ui/index.ts`
**修改点**:
1. `createClone` 方法增加:
- 调用 OpenClaw 内部 API 将分身添加到 `agents.list`
- 设置 `agentId` 字段关联分身与 Agent
2. `deleteClone` 方法增加:
- 从 `agents.list` 移除对应 Agent
3. `updateClone` 方法增加:
- 同步更新 Agent 配置
4. 新增 `zclaw.agents.sync` 方法:
- 读取当前 `agents.list`
- 与 `zclaw-data.json` 比对
- 修复不一致
### Task 2: 修改 GatewayClient - 支持 agentId
**文件**: `desktop/src/lib/gateway-client.ts`
**修改点**:
1. `chat()` 方法签名改为:
```typescript
async chat(message: string, opts?: {
agentId?: string; // 新增
sessionKey?: string;
model?: string;
}): Promise<{ runId: string; acceptedAt: string }>
```
2. `request('agent', ...)` 时传递 `agentId`
### Task 3: 修改 chatStore - 传递 agentId
**文件**: `desktop/src/store/chatStore.ts`
**修改点**:
1. `sendMessage` 方法调用 `client.chat()` 时传递 `currentAgent.id`
### Task 4: 新增配置 RPC 方法
**文件**: `desktop/src/lib/gateway-client.ts` + `plugins/zclaw-ui/index.ts`
**新增方法**:
- `zclaw.config.get` - 读取 OpenClaw 配置
- `zclaw.config.patch` - 修改配置(不重启)
- `zclaw.config.apply` - 热更新配置(如需重启)
### Task 5: 数据迁移脚本
**创建**: `scripts/migrate-clones-to-agents.ts`
**功能**:
1. 读取现有 `zclaw-data.json` 中的分身
2. 为每个分身在 `agents.list` 创建对应条目
3. 更新分身的 `agentId` 字段
4. 备份原始文件
---
## 九、验收标准
### P0 完成标准
- [ ] 创建分身后,`~/.openclaw/openclaw.json` 的 `agents.list` 包含新 Agent
- [ ] 删除分身后,对应 Agent 从 `agents.list` 移除
- [ ] 切换分身后,聊天请求携带正确的 `agentId`
- [ ] 每个分身有独立的对话上下文(不串聊)
- [ ] 现有分身数据成功迁移,无数据丢失
- [ ] 单元测试覆盖新增逻辑 ≥ 80%

View File

@@ -1,571 +0,0 @@
# ZCLAW 系统全面代码分析与演化路线图
## 上下文 (Context)
**目的**: 对 ZCLAW 系统进行全面的代码层面现状分析,识别偏离点、潜在风险,制定分阶段演化路线图。
**当前状态**:
- OpenFang v0.4.0 + ZClaw Desktop v0.2.0
- API 覆盖率: 93% (63/68 端点)
- UI 完成度: 100% (30/30 组件)
- Skills 定义: 68 个已完成
- Phase 1-8 已完成
**技术栈**:
- React 19.1.0 + TypeScript 5.8.3
- Tauri 2.x (Rust 后端)
- Zustand 5.0.11 (状态管理)
- Vite 7.0.4 + Tailwind CSS 4.2.1
---
## 一、代码结构分析
### 1.1 项目结构
```
ZClaw_openfang/
├── desktop/ # Tauri 桌面应用 (主要代码)
│ ├── src/
│ │ ├── components/ # React UI (46 组件)
│ │ ├── store/ # Zustand stores (3 个)
│ │ ├── lib/ # API 客户端和工具
│ │ ├── types/ # TypeScript 类型定义
│ │ └── App.tsx # 主应用组件
│ └── src-tauri/ # Rust 后端
├── skills/ # 68 个 SKILL.md 定义
├── hands/ # 7 个 HAND.toml 配置
├── config/ # OpenFang TOML 配置
├── tests/ # Vitest 测试
└── docs/ # 文档
```
### 1.2 核心数据流
```
React UI → Zustand Store → GatewayClient → OpenFang Kernel (端口 50051)
WebSocket (ws://127.0.0.1:50051/ws)
REST API (http://127.0.0.1:50051/api/*)
```
---
## 二、架构问题分析
### 2.1 Store 层问题 (高优先级)
| 问题 | 位置 | 影响 |
|------|------|------|
| **gatewayStore 巨型化** | `store/gatewayStore.ts` | 50+ 字段、40+ actions 在单一 store |
| **持久化策略不一致** | 所有 stores | chatStore 用 Zustand persistteamStore 手动 localStorage |
| **Agent/Clone ID 混淆** | `chatStore.ts` | 前端 `clone_` 前缀与后端 ID 不一致 |
### 2.2 安全问题 (关键)
| 问题 | 位置 | 严重程度 |
|------|------|----------|
| **Token 存储在 localStorage** | `gateway-client.ts:103` | HIGH |
| **Ed25519 密钥无加密** | `gateway-client.ts:157-188` | HIGH |
| **JSON.parse 无保护** | `HandParamsForm.tsx:409`, `WorkflowEditor.tsx:167` | HIGH |
| **默认使用 ws://** | `gateway-client.ts:20-22` | MEDIUM |
### 2.3 代码质量问题
| 问题 | 数量 | 主要位置 |
|------|------|----------|
| **`any` 类型滥用** | 60+ 处 | `gatewayStore.ts` (~35), `gateway-client.ts` (~12) |
| **错误处理不完整** | 多处 | 部分 catch 块静默忽略错误 |
| **测试覆盖不足** | - | `gateway-client.ts`, `toml-utils.ts` 无测试 |
| **代码重复** | 30+ 处 | 错误处理模式重复 |
### 2.4 性能问题
| 问题 | 位置 | 影响 |
|------|------|------|
| **消息数组频繁 map** | `chatStore.ts` | 长对话性能下降 |
| **无消息分页** | `chatStore.ts` | 内存持续增长 |
| **无 WebSocket 批处理** | `gateway-client.ts` | 高频消息处理效率低 |
---
## 三、分阶段演化路线图
### Phase 9: 安全加固 (1 周) - 3 代理并行
**目标**: 修复关键安全漏洞
#### 并行执行架构
```
┌─────────────────────────────────────────────────────────────┐
│ Agent A: JSON 安全 │ Agent B: Token 迁移 │
│ ├── lib/json-utils.ts │ ├── gateway-client.ts │
│ ├── HandParamsForm.tsx │ ├── gatewayStore.ts │
│ └── WorkflowEditor.tsx │ └── 迁移工具 │
├─────────────────────────────┼───────────────────────────────┤
│ Agent C: 加密增强 │ 完成后合并 → 文档更新 → 推送 │
│ ├── secure-storage.ts │ ├── docs/SYSTEM_ANALYSIS.md │
│ ├── secure_storage.rs │ ├── PROGRESS.md │
│ └── WSS 配置 │ └── git commit + push │
└─────────────────────────────┴───────────────────────────────┘
```
| 任务 | 文件 | 工作量 | 代理 |
|------|------|--------|------|
| 创建 `safeJsonParse<T>()` | `lib/json-utils.ts` | 4h | A |
| 替换不安全 JSON.parse | `HandParamsForm.tsx`, `WorkflowEditor.tsx` | 3h | A |
| Token 迁移到 secure-storage | `gateway-client.ts`, `gatewayStore.ts` | 6h | B |
| Ed25519 密钥加密 | `secure-storage.ts`, `secure_storage.rs` | 4h | C |
| 添加 WSS 配置 | `gateway-client.ts` | 2h | C |
**完成后同步**:
```bash
# 1. 更新文档
git add docs/SYSTEM_ANALYSIS.md PROGRESS.md
git commit -m "docs: update Phase 9 security hardening progress"
git push origin main
# 2. 代码提交
git add . && git commit -m "security(phase-9): complete security hardening
- Add safeJsonParse utility with schema validation
- Migrate tokens to OS keyring storage
- Add Ed25519 key encryption at rest
- Enable WSS configuration option
Co-Authored-By: Claude <noreply@anthropic.com>"
git push origin main
```
**验收标准**:
- [ ] 所有 JSON.parse 有 try-catch 保护
- [ ] Token 存储在 OS keyring
- [ ] TypeScript 编译通过
- [ ] 现有测试通过
- [ ] **文档已更新并推送**
---
### Phase 10: 类型安全强化 (1 周) - 3 代理并行
**目标**: 减少 `any` 使用,提升类型安全
#### 并行执行架构
```
┌─────────────────────────────────────────────────────────────┐
│ Agent A: API 类型 │ Agent B: Store 类型 │
│ ├── types/api-responses.ts │ ├── store/gatewayStore.ts │
│ ├── types/errors.ts │ └── 35 处 any 替换 │
│ └── 所有 API 响应类型化 │ │
├─────────────────────────────┼───────────────────────────────┤
│ Agent C: Client 类型 │ 完成后 → 统计 any 减少 → 推送 │
│ ├── lib/gateway-client.ts │ grep -r ": any" | wc -l │
│ └── 12 处 any 替换 │ git commit + push │
└─────────────────────────────┴───────────────────────────────┘
```
| 任务 | 文件 | 工作量 | 代理 |
|------|------|--------|------|
| 创建 API 响应类型 | `types/api-responses.ts` | 4h | A |
| 创建错误类型层级 | `types/errors.ts` | 2h | A |
| 替换 gatewayStore any | `store/gatewayStore.ts` (35处) | 8h | B |
| 替换 gateway-client any | `lib/gateway-client.ts` (12处) | 4h | C |
**完成后同步**:
```bash
# 统计并提交
echo "## Phase 10 类型安全 (完成)" >> docs/SYSTEM_ANALYSIS.md
git add . && git commit -m "refactor(phase-10): reduce any usage by 50%" && git push
```
**验收标准**:
- [ ] `any` 使用减少 50% (从 60+ 降到 30)
- [ ] 所有 API 响应有类型定义
- [ ] TypeScript strict mode 通过
- [ ] **文档已更新并推送**
---
### Phase 11: Store 重构 (2 周) - 分步并行
**目标**: 分解巨型 gatewayStore (1500+ 行)
**目标架构**:
```
gatewayStore (协调器, <100 行)
├── connectionStore (WebSocket, 认证, ~200 行)
├── agentStore (分身, 配置文件, ~200 行)
├── handStore (Hands, 触发器, ~200 行)
├── workflowStore (工作流, 执行历史, ~200 行)
└── configStore (设置, 工作区, ~200 行)
```
#### 分步并行执行
```
Step 1 (阻塞): 创建所有 store 接口定义 (1 天)
Step 2 (并行): 同时提取 connectionStore, agentStore, handStore (3 天)
Step 3 (并行): 同时提取 workflowStore, configStore (2 天)
Step 4 (阻塞): 创建协调层 + 更新组件导入 (3 天)
Step 5 (同步): 测试 + 文档更新 + 推送 (1 天)
```
| 任务 | 工作量 | 执行方式 |
|------|--------|----------|
| 创建 store 接口定义 | 1 天 | 阻塞 |
| 提取 connectionStore | 3 天 | 并行 A |
| 提取 agentStore | 3 天 | 并行 B |
| 提取 handStore | 3 天 | 并行 C |
| 提取 workflowStore | 2 天 | 并行 A |
| 提取 configStore | 2 天 | 并行 B |
| 创建协调层 + 组件更新 | 3 天 | 阻塞 |
**完成后同步**:
```bash
git add . && git commit -m "refactor(phase-11): decompose gatewayStore
- Extract connectionStore (WebSocket, auth)
- Extract agentStore (clones, profiles)
- Extract handStore (hands, triggers)
- Extract workflowStore (workflows, runs)
- Extract configStore (settings, workspace)
- Add coordinator layer
Each store now < 300 lines with clear separation of concerns.
Co-Authored-By: Claude <noreply@anthropic.com>"
git push origin main
```
**验收标准**:
- [ ] 每个 store < 300
- [ ] 清晰的关注点分离
- [ ] 所有组件正常工作
- [ ] **文档已更新并推送**
---
### Phase 12: 性能优化 (1 周) - 2 代理并行
**目标**: 优化消息处理和渲染
#### 并行执行架构
```
┌─────────────────────────────────────────────────────────────┐
│ Agent A: 消息渲染优化 │ Agent B: WebSocket 优化 │
│ ├── ChatArea.tsx 虚拟化 │ ├── gateway-client.ts │
│ ├── chatStore.ts 分页 │ ├── 消息批处理 │
│ └── lib/message-cache.ts │ └── 节流/防抖 │
└─────────────────────────────┴───────────────────────────────┘
```
| 任务 | 文件 | 工作量 | 代理 |
|------|------|--------|------|
| 实现消息虚拟化 | `ChatArea.tsx` | 8h | A |
| 添加消息分页 | `chatStore.ts` | 6h | A |
| 实现 LRU 消息缓存 | `lib/message-cache.ts` | 4h | A |
| WebSocket 消息批处理 | `gateway-client.ts` | 4h | B |
**完成后同步**:
```bash
git add . && git commit -m "perf(phase-12): optimize message handling
- Add message virtualization for long conversations
- Implement message pagination in chatStore
- Add LRU cache for rendered messages
- Add WebSocket message batching
Handles 10k+ messages without performance degradation.
Co-Authored-By: Claude <noreply@anthropic.com>"
git push origin main
```
**验收标准**:
- [ ] 支持 10,000+ 消息无性能下降
- [ ] 内存使用保持稳定
- [ ] 滚动流畅
- [ ] **文档已更新并推送**
---
### Phase 13: 测试覆盖 (1 周) - 3 代理并行
**目标**: 建立完整测试体系达到 80% 覆盖率
#### 并行执行架构
```
┌─────────────────────────────────────────────────────────────┐
│ Agent A: 核心模块测试 │ Agent B: 工具模块测试 │
│ ├── gateway-client.test.ts │ ├── secure-storage.test.ts │
│ ├── 连接生命周期测试 │ ├── toml-utils.test.ts │
│ └── 消息帧解析测试 │ └── json-utils.test.ts │
├─────────────────────────────┼───────────────────────────────┤
│ Agent C: 集成测试 │ 完成后 → 覆盖率报告 → 推送 │
│ ├── chat-flow.test.ts │ pnpm vitest --coverage │
│ └── React 组件测试 │ git commit + push │
└─────────────────────────────┴───────────────────────────────┘
```
| 任务 | 文件 | 工作量 | 代理 |
|------|------|--------|------|
| gateway-client 单元测试 | `tests/desktop/gateway-client.test.ts` | 6h | A |
| secure-storage 单元测试 | `tests/desktop/secure-storage.test.ts` | 2h | B |
| toml-utils 单元测试 | `tests/desktop/toml-utils.test.ts` | 2h | B |
| json-utils 单元测试 | `tests/desktop/json-utils.test.ts` | 2h | B |
| 聊天流程集成测试 | `tests/desktop/integration/chat-flow.test.ts` | 4h | C |
| React 组件测试 | `tests/desktop/components/` | 8h | C |
**完成后同步**:
```bash
# 生成覆盖率报告
pnpm vitest run --coverage
git add . && git commit -m "test(phase-13): achieve 80% test coverage
- Add gateway-client unit tests
- Add secure-storage, toml-utils, json-utils tests
- Add chat flow integration tests
- Add React component tests
Coverage: 80%+ for core modules.
Co-Authored-By: Claude <noreply@anthropic.com>"
git push origin main
```
**验收标准**:
- [ ] 核心模块测试覆盖率 > 80%
- [ ] 关键用户流程有集成测试
- [ ] CI/CD 流水线通过
- [ ] **文档已更新并推送**
---
## 四、关键文件清单
### 需要修改的文件
| 优先级 | 文件路径 | 修改类型 |
|--------|----------|----------|
| P0 | `desktop/src/lib/gateway-client.ts` | 安全修复, 类型安全 |
| P0 | `desktop/src/store/gatewayStore.ts` | 重构分解, 类型安全 |
| P0 | `desktop/src/components/HandParamsForm.tsx` | JSON 解析安全 |
| P0 | `desktop/src/components/WorkflowEditor.tsx` | JSON 解析安全 |
| P1 | `desktop/src/store/chatStore.ts` | 性能优化 |
| P1 | `desktop/src/lib/secure-storage.ts` | 密钥加密 |
| P1 | `desktop/src-tauri/src/secure_storage.rs` | Rust 安全存储 |
### 需要创建的文件
| 文件路径 | 用途 |
|----------|------|
| `desktop/src/lib/json-utils.ts` | 安全 JSON 解析 |
| `desktop/src/types/api-responses.ts` | API 响应类型 |
| `desktop/src/types/errors.ts` | 错误类型定义 |
| `desktop/src/lib/message-cache.ts` | 消息 LRU 缓存 |
| `desktop/src/store/connectionStore.ts` | 连接状态管理 |
| `desktop/src/store/agentStore.ts` | Agent 管理 |
| `desktop/src/store/handStore.ts` | Hand 管理 |
| `desktop/src/store/workflowStore.ts` | 工作流管理 |
| `tests/desktop/gateway-client.test.ts` | 客户端测试 |
---
## 五、多代理并行执行策略
### 5.1 并行执行原则
**核心原则**: 独立任务并行执行,依赖任务顺序执行
```
┌─────────────────────────────────────────────────────────────────┐
│ 多代理并行执行架构 │
├─────────────────────────────────────────────────────────────────┤
│ │
│ Phase 9 (安全修复) - 并行执行: │
│ ├── Agent A: JSON 安全包装 + 输入验证 │
│ ├── Agent B: Token 迁移到 secure-storage │
│ └── Agent C: WSS 配置 + 密钥加密 │
│ │
│ Phase 10 (类型安全) - 并行执行: │
│ ├── Agent A: API 响应类型定义 │
│ ├── Agent B: gatewayStore any 替换 │
│ └── Agent C: gateway-client any 替换 │
│ │
│ Phase 11 (Store 重构) - 顺序执行 + 并行提取: │
│ ├── Step 1: 创建接口定义 (阻塞) │
│ ├── Step 2: 并行提取 connectionStore, agentStore, handStore │
│ ├── Step 3: 并行提取 workflowStore, configStore │
│ └── Step 4: 协调层 + 组件更新 │
│ │
│ Phase 12-13 (性能+测试) - 并行执行: │
│ ├── Agent A: 消息虚拟化 + 分页 │
│ ├── Agent B: WebSocket 批处理优化 │
│ └── Agent C: 测试编写 (与 A/B 同步) │
│ │
└─────────────────────────────────────────────────────────────────┘
```
### 5.2 代理分工
| 代理类型 | 职责 | 适用阶段 |
|----------|------|----------|
| **Security Engineer** | 安全修复、加密、Token 迁移 | Phase 9 |
| **Senior Developer** | 类型定义、Store 重构 | Phase 10-11 |
| **Frontend Developer** | UI 组件、性能优化 | Phase 12 |
| **Test Engineer** | 单元测试、集成测试 | Phase 13 |
| **Documentation Writer** | 文档更新、CHANGELOG | 所有阶段 |
### 5.3 每阶段完成后的同步动作
```bash
# 每个阶段完成后必须执行:
# 1. 更新相关文档
# - docs/SYSTEM_ANALYSIS.md (添加 Phase 进度)
# - docs/DEVELOPMENT.md (如有新开发指南)
# - PROGRESS.md (进度追踪)
# 2. 提交到仓库
git add .
git commit -m "feat(phase-N): 完成阶段任务描述
- 具体改动 1
- 具体改动 2
Co-Authored-By: Claude <noreply@anthropic.com>"
# 3. 推送到远程
git push origin main
```
### 5.4 文档更新检查清单
每个阶段完成后必须更新:
- [ ] `docs/SYSTEM_ANALYSIS.md` - 添加 Phase 完成记录
- [ ] `PROGRESS.md` - 更新进度百分比
- [ ] `CLAUDE.md` - 如有新的开发规范
- [ ] `README.md` - 如有新功能或依赖变更
---
## 六、资源需求 (多代理优化后)
### 时间估算对比
| 阶段 | 串行执行 | 3代理并行 | 节省 |
|------|----------|-----------|------|
| Phase 9 (安全) | 2 周 | **1 周** | 50% |
| Phase 10 (类型) | 2 周 | **1 周** | 50% |
| Phase 11 (Store重构) | 3 周 | **2 周** | 33% |
| Phase 12 (性能) | 2 周 | **1 周** | 50% |
| Phase 13 (测试) | 2 周 | **1 周** | 50% |
| **总计** | **11 周** | **6 周** | **45%** |
### 代理配置
| 阶段 | 所需代理 | 技能要求 |
|------|----------|----------|
| Phase 9 | 3 并行 | Security Engineer, Backend Dev, Rust Dev |
| Phase 10 | 3 并行 | TypeScript Expert, Frontend Dev |
| Phase 11 | 3 并行 → 顺序 | Senior Developer, State Management Expert |
| Phase 12 | 2 并行 | Frontend Dev, Performance Engineer |
| Phase 13 | 3 并行 | Test Engineer, Integration Specialist |
### 技能矩阵
| 技能 | Phase 9 | Phase 10 | Phase 11 | Phase 12 | Phase 13 |
|------|---------|----------|----------|----------|----------|
| TypeScript | 高 | 高 | 高 | 高 | 高 |
| React | 中 | 中 | 高 | 高 | 中 |
| Tauri/Rust | 高 | 低 | 低 | 低 | 低 |
| WebSocket | 高 | 中 | 中 | 高 | 中 |
| 状态管理 | 中 | 中 | 高 | 高 | 中 |
| 安全 | 高 | 中 | 中 | 低 | 中 |
| 测试 | 中 | 中 | 高 | 中 | 高 |
---
## 七、风险评估
| 风险 | 概率 | 影响 | 缓解措施 |
|------|------|------|----------|
| Store 重构破坏现有功能 | 中 | 高 | 重构前完善测试覆盖 |
| 持久化迁移丢失数据 | 低 | 严重 | 迁移工具, 回滚能力 |
| ID 标准化破坏 API 通信 | 中 | 高 | 集成测试验证 |
| 性能优化引入新 bug | 中 | 中 | 渐进式发布, 功能开关 |
---
## 七、成功指标
### Phase 9-10 指标
- [ ] 零安全漏洞 (静态分析)
- [ ] `any` 使用减少 50%
- [ ] 所有 Token 在安全存储中
### Phase 11 指标
- [ ] 所有 store < 300
- [ ] 清晰的关注点分离
- [ ] 持久化策略一致
### Phase 12-13 指标
- [ ] 10k+ 消息无性能下降
- [ ] UI 响应时间 < 100ms
- [ ] 测试覆盖率 > 80%
---
## 八、验证计划
### 自动化验证
```bash
# TypeScript 类型检查
pnpm tsc --noEmit
# 单元测试
pnpm vitest run
# 安全审计
pnpm audit
```
### 手动验证
1. 连接 OpenFang (端口 50051)
2. 发送消息并验证流式返回
3. 触发 Hand 并验证执行
4. 保存配置并验证持久化
5. 测试长对话性能 (>1000 消息)
---
## 九、执行时间表 (6 周计划)
```
周次 Phase 任务 代理数 交付物
─────────────────────────────────────────────────────────────────
W1 Phase 9 安全加固 3 并行 安全修复完成 + 文档
W2 Phase 10 类型安全强化 3 并行 类型定义 + any 减少 50%
W3-4 Phase 11 Store 重构 3 → 顺序 5 个子 Store + 协调层
W5 Phase 12 性能优化 2 并行 消息虚拟化 + 批处理
W6 Phase 13 测试覆盖 3 并行 80% 覆盖率 + CI 通过
─────────────────────────────────────────────────────────────────
完成 全部 Phase 9-13 文档更新 + 推送
```
---
*计划创建: 2026-03-15*
*多代理并行执行: 3 代理同时工作*
*预计完成: 6 周 (从 11 周优化 45%)*
*每阶段完成后: 文档更新 + Git 推送*

View File

@@ -1,589 +0,0 @@
# ZCLAW 项目深度分析与头脑风暴
## 一、项目全景概览
### 1.1 项目定位
ZCLAW 是一个**基于 OpenClaw 框架的定制化中文 AI 助手平台**,对标 AutoClaw (智谱) 和 QClaw (腾讯)。
**核心价值主张**
```
OpenClaw Gateway (成熟执行引擎)
↕ WebSocket Protocol v3
ZCLAW Tauri App (轻量桌面 UI)
+ 中文模型 Provider (GLM/Qwen/Kimi/MiniMax)
+ 飞书 Channel Plugin
+ 分身(Clone) 管理系统
+ 自定义 Skills
```
### 1.2 架构演进历程
| 阶段 | 架构方向 | 状态 |
|------|----------|------|
| v1 | 自建 AI Agent 框架 (src/core/*) | 🗑️ 已归档 |
| v2 | 基于 OpenClaw + Tauri | ✅ 当前方向 |
**架构转向原因**v1 偏离初衷约 75%,重复造轮子而非复用 OpenClaw 生态。
### 1.3 技术栈一览
| 层级 | 技术 | 版本 |
|------|------|------|
| 执行引擎 | OpenClaw Gateway | Node.js daemon |
| 桌面壳 | Tauri | 2.0 |
| 前端框架 | React | 19.1.0 |
| 状态管理 | Zustand | 5.0.11 |
| 样式 | TailwindCSS | 4.2.1 |
| 构建工具 | Vite | 7.0.4 |
| 语言 | TypeScript | 5.8.3 |
| 通信协议 | WebSocket | Gateway Protocol v3 |
---
## 二、当前项目状态
### 2.1 已完成阶段
| Phase | 内容 | 完成度 |
|-------|------|--------|
| Phase 1 | 后端 Gateway 层 + 插件 + Skills | ✅ 100% |
| Phase 2 | 前端 Settings 页面体系 (10页) | ✅ 100% |
| Phase 3 | 聊天对接 + 分身管理 | ✅ 100% |
| Phase 3.5 | 前端质量提升 | ✅ 100% |
| Phase 4 | OpenClaw 真实集成测试 | ⏳ 待开始 |
| Phase 5 | Tauri Rust sidecar + 打包发布 | 📋 规划中 |
### 2.2 代码统计
| 类别 | 文件数 | 说明 |
|------|--------|------|
| Gateway 层 | 3 | manager.ts, ws-client.ts, index.ts |
| 插件 | 6 | 3 plugins × (index.ts + plugin.json) |
| Skills | 2 | 2 × SKILL.md |
| 配置 | 5 | 1 JSON + 4 MD |
| 前端组件 | 15+ | 组件/Store/工具库 |
| v1 遗留代码 | 37+ | src/core/* (已归档) |
### 2.3 编译状态
- TypeScript: **0 errors**
- Vite build: **成功** (1766 modules, 268 KB JS + 26 KB CSS)
---
## 三、核心模块深度分析
### 3.1 OpenClaw Gateway 集成层 (src/gateway/)
#### manager.ts - 子进程管理器
```
功能: 管理 OpenClaw Gateway 子进程生命周期
特性:
- 启动/停止 Gateway daemon
- 健康检查 (HTTP 探测)
- 自动重启 (最多 5 次)
- 连接外部已运行实例
```
#### ws-client.ts - WebSocket 客户端
```
功能: 实现 OpenClaw Gateway Protocol v3
特性:
- 三步握手 (challenge → connect → hello-ok)
- 请求/响应模式 (30秒超时)
- 事件订阅 (agent/chat/presence/health/heartbeat)
- 自动重连 (指数退避 1.5x, 最大 30s)
```
### 3.2 自定义插件系统 (plugins/)
#### @zclaw/chinese-models - 中文模型 Provider
| Provider | 模型 |
|----------|------|
| 智谱 GLM | glm-5, glm-4.7, glm-4-plus, glm-4-flash |
| 通义千问 | qwen3.5-plus, qwen-max, qwen-vl-max |
| Kimi | kimi-k2.5, moonshot-v1-128k |
| MiniMax | minimax-m2.5, abab6.5s-chat |
**设计特点**: 全部使用 OpenAI 兼容 API 格式,支持自定义 Base URL。
#### @zclaw/feishu - 飞书 Channel Plugin
```
功能: 将飞书注册为 OpenClaw 消息渠道
特性:
- OAuth tenant_access_token 管理 (2h 有效期, 1.5h 刷新)
- 文本/富文本消息发送
- 多账户支持
```
#### @zclaw/ui - UI 扩展 RPC
| 方法 | 功能 |
|------|------|
| zclaw.clones.* | 分身 CRUD |
| zclaw.stats.* | 用量/会话统计 |
| zclaw.config.quick | 快速配置 |
| zclaw.workspace.info | 工作区信息 |
| zclaw.plugins.status | 插件状态 |
### 3.3 前端架构 (desktop/src/)
#### 三层布局
```
┌─────────────────────────────────────────────────────────┐
│ Sidebar (w-64) │ ChatArea (flex-1) │ RightPanel (w-72) │
│ 左侧边栏 │ 中间对话区 │ 右侧边栏 │
└─────────────────────────────────────────────────────────┘
```
#### 状态管理 (Zustand)
- **chatStore**: 消息/对话/Agent/流式状态
- **gatewayStore**: 连接/分身/统计/插件状态
#### 关键组件
| 组件 | 职责 |
|------|------|
| ChatArea | 消息展示 + 流式输出 + Markdown渲染 + 模型选择 |
| Sidebar | 四标签 (对话/分身/频道/任务) |
| RightPanel | Gateway状态 + 会话统计 + 插件状态 |
| Settings/* | 10个设置页面对标 AutoClaw |
### 3.4 v1 遗留代码 (已归档)
以下代码位于 `src/core/` 等目录,已从编译范围排除:
| 模块 | 状态 | 替代方案 |
|------|------|----------|
| remote-execution/ | 🗑️ | OpenClaw 工具执行 |
| task-orchestration/ | 🗑️ | OpenClaw Agent Loop |
| multi-agent/ | 🗑️ | OpenClaw agents.list |
| memory/ | 🗑️ | OpenClaw Memory Plugin |
| proactive/ | 🗑️ | OpenClaw Heartbeat Engine |
| im/ | 🗑️ | OpenClaw Channel 系统 |
| db/ | 🗑️ | OpenClaw 自带 SQLite |
| config/ | 🗑️ | OpenClaw 配置系统 |
| api/ | 🗑️ | WebSocket + Tauri Commands |
---
## 四、头脑风暴:机会与挑战
### 4.1 架构优势 💪
1. **复用成熟生态**
- OpenClaw 28万+ Stars工具执行/Skills/MCP/心跳引擎成熟
- 避免重复造轮子,专注差异化价值
2. **Tauri 轻量化**
- ~10MB vs Electron ~150MB
- Rust native 性能优异
- 系统级集成能力
3. **中文优先定位**
- 4大中文模型原生支持
- 飞书/微信/QQ 等 IM 渠道
4. **模块化插件设计**
- Provider/Channel/RPC 插件独立开发
- 可扩展性强
### 4.2 潜在风险 ⚠️
1. **OpenClaw 依赖**
- 版本兼容性风险
- 文档/社区支持限制
2. **v1 遗留代码清理**
- 37+ 文件需要决策 (保留/删除/重构)
- 可能存在可复用的代码片段
3. **Tauri 后端功能有限**
- 当前 Rust 代码几乎为空
- 需要实现 sidecar/文件系统/通知等
4. **测试覆盖不足**
- 未见测试文件
- 集成测试缺失
### 4.3 创新机会 💡
#### A. 分身系统增强
```
当前: 基础 CRUD
增强方向:
- 分身间协作 (多 Agent 编排)
- 分身记忆隔离/共享
- 分身能力画像 (擅长领域)
- 分身市场 (社区分享)
```
#### B. Skills 生态扩展
```
当前: 2 个基础 Skills
扩展方向:
- 社媒运营套件 (微博/小红书/抖音)
- 学术研究助手 (论文/文献/翻译)
- 代码审查专家 (PR Review/安全审计)
- 数据分析专家 (SQL/报表/可视化)
```
#### C. IM 渠道深化
```
当前: 飞书基础支持
深化方向:
- 微信企业号 (WeCom API)
- QQ 机器人 (NapCat/Go-CQHTTP)
- 钉钉/飞书/企业微信三合一
- 消息路由规则 (关键词/时间/来源)
```
#### D. 工作区智能化
```
当前: 基础目录配置
智能方向:
- 项目上下文感知 (package.json/README 解析)
- 代码库索引 (LSP 集成)
- 文件变更监听 (自动同步理解)
- 多工作区切换
```
#### E. 数据分析增强
```
当前: 基础用量统计
增强方向:
- 对话质量分析 (满意度/解决率)
- Token 成本优化建议
- 使用模式洞察 (高峰时段/常用功能)
- 导出报告 (PDF/Excel)
```
### 4.4 技术改进建议 🔧
#### 短期 (1-2周)
1. **完成 Phase 4 集成测试**
- 安装并验证 OpenClaw
- 测试 Gateway 连接
- 验证插件注册
- 端到端消息收发测试
2. **清理 v1 遗留代码**
- 评估每模块的可复用性
- 删除确定无用的代码
- 保留有价值的工具函数
3. **补充基础测试**
- Gateway 协议单元测试
- 前端组件测试
- E2E 关键流程测试
#### 中期 (1-2月)
1. **Tauri Rust 后端扩展**
- Gateway sidecar 管理
- 系统托盘集成
- 原生通知
- 文件系统访问
2. **微信/QQ Channel Plugin**
- 调研 NapCat/Go-CQHTTP
- 实现 Channel Plugin 接口
3. **Skills 扩展**
- 社媒运营套件
- 代码审查助手
#### 长期 (3-6月)
1. **多 Agent 协作可视化**
- 任务依赖图
- 执行进度追踪
- 结果聚合展示
2. **插件市场**
- 插件发现/安装/更新
- 社区贡献机制
3. **移动端伴侣 App**
- Flutter/React Native
- 与桌面端数据同步
---
## 五、竞品对标分析
| 维度 | AutoClaw (智谱) | QClaw (腾讯) | ZCLAW |
|------|----------------|--------------|-------|
| 基础框架 | OpenClaw | OpenClaw | OpenClaw |
| IM 渠道 | 飞书 | 微信+QQ | 飞书 (计划微信/QQ) |
| 桌面框架 | 自研 | Electron | Tauri 2.0 |
| 模型支持 | GLM 系列 | 腾讯混元 | GLM/Qwen/Kimi/MiniMax |
| 安装包大小 | 未知 | ~150MB | ~10MB (目标) |
| 开源状态 | 未开源 | 未开源 | MIT 开源 |
**差异化优势**
- 🦀 Tauri 轻量化
- 🌐 多中文模型支持
- 🔓 开源可定制
- 🧩 插件生态开放
---
## 六、下一步行动计划
### Phase 4: 真实集成测试 (当前优先级)
```
[ ] 1. 安装 OpenClaw
- Windows: iwr -useb https://openclaw.ai/install.ps1 | iex
- 验证: openclaw --version
[ ] 2. 配置 Gateway
- 运行 openclaw configure
- 填入 API Key (智谱/通义/Kimi 任选)
[ ] 3. 启动 Gateway
- openclaw gateway
- 验证: curl http://127.0.0.1:18789/health
[ ] 4. 注册 ZCLAW 插件
- pnpm setup
- 验证插件加载
[ ] 5. 前端连接测试
- cd desktop && pnpm tauri dev
- 验证 WebSocket 连接
- 测试消息收发
[ ] 6. 飞书 Channel 测试
- 配置飞书应用凭证
- 测试消息收发
```
### Phase 5: 打包发布准备
```
[ ] Tauri Rust sidecar 实现
[ ] 安装包测试 (Windows/macOS/Linux)
[ ] 自动更新机制
[ ] 文档完善
[ ] 发布 v0.1.0
```
---
## 七、总结
ZCLAW 是一个定位清晰的 OpenClaw 定制化项目,通过复用成熟生态 + Tauri 轻量桌面 + 中文优先策略,有望成为开源领域的 AutoClaw/QClaw 替代方案。
**核心建议**
1. 🎯 聚焦 Phase 4 集成测试,打通端到端流程
2. 🧹 清理 v1 遗留代码,减少维护负担
3. ✅ 补充测试覆盖,提升代码质量
4. 🚀 迭代发布,快速验证市场反馈
---
---
## 八、执行路线图 (用户选择)
基于用户反馈,将并行推进以下四个方向:
### 8.1 Phase 4: 真实集成测试 🔌
**目标**: 打通 OpenClaw Gateway ↔ ZCLAW Tauri 端到端流程
**任务清单**:
```
[ ] 安装 OpenClaw CLI
- Windows: iwr -useb https://openclaw.ai/install.ps1 | iex
- 验证: openclaw --version
[ ] 配置 Gateway
- 运行 openclaw configure
- 配置 API Key (智谱 GLM 作为首选)
[ ] 启动 Gateway daemon
- openclaw gateway --port 18789
- 验证: curl http://127.0.0.1:18789/health
[ ] 注册 ZCLAW 插件
- pnpm setup (执行 scripts/setup.ts)
- 验证插件加载: openclaw plugins list
[ ] 前端连接测试
- cd desktop && pnpm tauri dev
- 验证 WebSocket 连接成功
- 测试消息发送和流式接收
[ ] 飞书 Channel 测试 (可选)
- 配置飞书应用凭证
- 测试飞书消息收发
```
**验收标准**:
- ✅ Gateway 启动成功,健康检查通过
- ✅ 前端显示"已连接"状态
- ✅ 发送消息能收到 AI 流式回复
- ✅ 模型切换功能正常
### 8.2 清理 v1 遗留代码 🧹
**目标**: 评估并处理 src/core/ 等 37+ 个归档文件
**待处理目录**:
| 目录 | 文件数 | 建议操作 |
|------|--------|----------|
| src/core/remote-execution/ | ~4 | 🗑️ 删除 (OpenClaw 替代) |
| src/core/task-orchestration/ | ~3 | 🗑️ 删除 (OpenClaw 替代) |
| src/core/multi-agent/ | ~8 | 🗑️ 删除 (OpenClaw 替代) |
| src/core/memory/ | ~2 | 🗑️ 删除 (OpenClaw 替代) |
| src/core/proactive/ | ~2 | 🗑️ 删除 (OpenClaw 替代) |
| src/core/ai/ | ~6 | ⚠️ 评估 (可能复用 Provider) |
| src/im/ | ~4 | 🗑️ 删除 (OpenClaw 替代) |
| src/db/ | ~3 | 🗑️ 删除 (OpenClaw 替代) |
| src/config/ | ~2 | 🗑️ 删除 (OpenClaw 替代) |
| src/api/ | ~1 | 🗑️ 删除 (WebSocket 替代) |
| src/app.ts | 1 | 🗑️ 删除 |
| src/index.ts | 1 | 🔄 重写为简单入口 |
**任务清单**:
```
[ ] 创建 archive/v1-backup 分支保存当前状态
[ ] 评估 src/core/ai/ 的可复用性
- providers/zhipu.ts 可能对插件开发有参考价值
- manager.ts 的 fallback 逻辑可借鉴
[ ] 删除确认无用的目录
[ ] 重写 src/index.ts 为最小化入口
[ ] 更新 tsconfig.json 移除对旧代码的引用
[ ] 验证编译: pnpm build (0 errors)
```
**验收标准**:
- ✅ v1 代码已备份到独立分支
- ✅ 主分支代码精简,无死代码
- ✅ TypeScript 编译 0 errors
- ✅ 项目结构清晰,符合 v2 架构
### 8.3 补充测试覆盖 ✅
**目标**: 建立基础测试框架,覆盖关键模块
**测试分层**:
```
tests/
├── unit/ # 单元测试
│ ├── gateway/
│ │ ├── manager.test.ts # 子进程管理
│ │ └── ws-client.test.ts # WebSocket 客户端
│ └── utils/
│ ├── logger.test.ts
│ └── id.test.ts
├── integration/ # 集成测试
│ ├── gateway-protocol.test.ts # Gateway 协议
│ └── plugin-loading.test.ts # 插件加载
└── e2e/ # 端到端测试
└── chat-flow.test.ts # 完整对话流程
```
**任务清单**:
```
[ ] 配置测试框架
- 安装 Vitest + @testing-library/react
- 配置 vitest.config.ts
[ ] Gateway 层单元测试
- ws-client.ts: 握手流程、重连逻辑
- manager.ts: 进程管理、健康检查
[ ] 前端组件测试
- chatStore: 消息发送、流式处理
- gatewayStore: 连接状态管理
- ChatArea: 消息渲染、输入处理
[ ] 集成测试
- Gateway Protocol v3 完整握手
- 插件注册和 RPC 调用
[ ] CI 集成
- GitHub Actions 自动运行测试
- 覆盖率报告
```
**验收标准**:
- ✅ 测试框架配置完成
- ✅ 核心模块测试覆盖率 > 60%
- ✅ CI 流水线运行成功
### 8.4 扩展 Skills/插件 🧩
**目标**: 丰富 Skills 生态,增加 IM 渠道支持
**Skills 扩展计划**:
| Skill | 触发词 | 功能 |
|-------|--------|------|
| social-media | 发微博/小红书/抖音 | 社媒内容创作和发布 |
| code-review | 审查代码/PR Review | 代码质量分析和建议 |
| data-analysis | 分析数据/生成报表 | SQL 查询和可视化 |
| translation | 翻译/中译英 | 多语言翻译 |
**插件扩展计划**:
| 插件 | 类型 | 优先级 |
|------|------|--------|
| @zclaw/wechat | Channel | 高 |
| @zclaw/qq | Channel | 高 |
| @zclaw/terminal | Tool | 中 |
| @zclaw/advanced-memory | Memory | 中 |
**任务清单**:
```
[ ] Skills 开发
- 创建 skills/social-media/SKILL.md
- 创建 skills/code-review/SKILL.md
- 创建 skills/data-analysis/SKILL.md
- 创建 skills/translation/SKILL.md
[ ] 微信 Channel Plugin 调研
- 评估 WeCom API 可行性
- 评估 NapCat/Go-CQHTTP 桥接方案
- 输出技术方案文档
[ ] QQ Channel Plugin 调研
- 评估 NapCatQQ 方案
- 输出技术方案文档
[ ] 插件开发 (选一个优先)
- 实现微信或 QQ Channel Plugin
```
**验收标准**:
- ✅ 至少 2 个新 Skills 可用
- ✅ 微信/QQ 技术方案文档完成
- ✅ 至少 1 个新 Channel Plugin 可测试
---
## 九、执行优先级排序
基于依赖关系和价值,建议执行顺序:
```
第 1 周: Phase 4 集成测试 + v1 代码清理
└─ 这两项可以并行,互不依赖
第 2 周: 补充测试覆盖
└─ 在集成测试通过后补充自动化测试
第 3-4 周: Skills/插件扩展
└─ 在稳定基础上扩展功能
```
**里程碑**:
- 🏁 Week 1 结束: 端到端流程打通 + 代码库精简
- 🏁 Week 2 结束: 测试覆盖率 > 60%
- 🏁 Week 4 结束: 4+ 新 Skills + 1 新 Channel Plugin
---
*分析完成于 2026-03-12*
*执行计划更新于 2026-03-12*

View File

@@ -1,243 +0,0 @@
# ZCLAW 系统偏离分析与演化路线图更新方案
**分析日期**: 2026-03-15
**目的**: 基于代码层面深度分析,更新系统偏离点,制定下一阶段演化路线
**状态**: ✅ **全部完成**
---
## 一、背景与上下文
### 1.1 为什么需要这次分析?
现有的 [SYSTEM_ANALYSIS.md](docs/SYSTEM_ANALYSIS.md) 记录了 Phase 1-5 的完成状态和 Phase 6 的进行中状态。但代码层面的深度分析发现了新的偏离点,特别是:
1. **Team 协作功能** - 文档标记为"进行中",但代码显示 `teamStore.ts` 完全使用 localStorage 而非真实 API
2. **REST API 认证缺失** - WebSocket 有完整认证REST 请求无认证头
3. **设置持久化问题** - 主题/自动启动等设置仅改变本地状态
4. **编辑模式不完整** - WorkflowEditor 编辑时不加载现有步骤
### 1.2 分析方法
使用 3 个并行 Explore 代理深度分析:
- 前端组件和 UI 状态管理
- OpenFang 通信层实现
- 配置和技能系统
### 1.3 实施方法
使用多代理并行执行:
- 14 个专业代理并行工作
- TypeScript + Rust 双重验证
- 所有修改通过 `pnpm tsc --noEmit``cargo check`
---
## 二、新发现的偏离点
### 2.1 关键数据流断裂 (P0 - 最高优先级)
| ID | 组件 | 问题描述 | 影响 |
|----|------|----------|------|
| **A1** | [teamStore.ts](desktop/src/store/teamStore.ts) | 所有 CRUD 操作使用 localStorage从未调用 [team-client.ts](desktop/src/lib/team-client.ts) API | Team 协作功能完全虚假 |
| **A2** | [WorkflowEditor.tsx:217](desktop/src/components/WorkflowEditor.tsx#L217) | 编辑模式初始化空步骤,不加载现有工作流 | 无法编辑真实工作流 |
| **A3** | [SchedulerPanel.tsx:649](desktop/src/components/SchedulerPanel.tsx#L649) | 事件触发器创建显示占位 alert | 无法创建事件触发器 |
### 2.2 安全与配置偏离 (P0-P1)
| ID | 组件 | 问题描述 | 影响 |
|----|------|----------|------|
| **B1** | [gateway-client.ts](desktop/src/lib/gateway-client.ts) | REST API 请求不携带认证头 | 未认证的 REST 调用 |
| **B2** | [gateway-client.ts](desktop/src/lib/gateway-client.ts) | Token 存储在 localStorage | 敏感数据不安全存储 |
| **B3** | [General.tsx:9-11](desktop/src/components/Settings/General.tsx#L9-L11) | 主题/自动启动仅改变本地 state | 设置不持久化到 TOML |
### 2.3 端口与文档偏离
| 来源 | 端口 | 状态 |
|------|------|------|
| **实际 OpenFang** | 50051 | 代码正确适配 |
| **文档** | 4200 | 需更新 |
| **FALLBACK_GATEWAY_URLS** | 50051, 4200 | 回退列表包含两个 |
---
## 三、演化路线图 (更新版) - ✅ 全部完成
### Phase 0: 稳定化修复 ✅ 完成
**目标**: 修复关键数据流断裂问题
| 任务 | 状态 | 文件 |
|------|------|------|
| Team Store API 集成 | ✅ 完成 | `teamStore.ts` - 替换 localStorage 为 API |
| REST API 认证 | ✅ 完成 | `team-client.ts` - 添加 `getAuthHeaders()` |
| Workflow 编辑器步骤加载 | ✅ 完成 | `WorkflowEditor.tsx` - 编辑模式加载步骤 |
### Phase 1: 功能对齐 ✅ 完成
**目标**: 连接所有 UI 组件到真实 OpenFang 能力
| 任务 | 状态 | 文件 |
|------|------|------|
| 事件触发器创建 | ✅ 完成 | `CreateTriggerModal.tsx` (新建) |
| 设置持久化 | ✅ 完成 | `General.tsx` - 连接 gatewayStore |
| WebSocket 团队事件订阅 | ✅ 完成 | `useTeamEvents.ts`, `teamStore.ts` |
| 安全 Token 存储 | ✅ 完成 | `secure_storage.rs` (新建), `secure-storage.ts` (新建) |
### Phase 2: 架构优化 ✅ 完成
**目标**: 改善系统架构以提高可维护性和性能
| 任务 | 状态 | 文件 |
|------|------|------|
| TOML 配置支持 | ✅ 完成 | `toml-utils.ts`, `config-parser.ts`, `types/config.ts` |
| 请求超时和重试 | ✅ 完成 | `request-helper.ts` (新建) |
### Phase 3: 扩展和增强 ✅ 完成
**目标**: 完善 OpenFang 特有功能的 UI
| 任务 | 状态 | 文件 |
|------|------|------|
| 16 层安全状态 UI | ✅ 完成 | `SecurityLayersPanel.tsx` (新建) |
| Hand 审批工作流 | ✅ 完成 | `HandApprovalModal.tsx`, `ApprovalsPanel.tsx` |
| 增强 Hand 参数 UI | ✅ 完成 | `HandParamsForm.tsx` (新建) |
| 审计日志查看器 | ✅ 完成 | `AuditLogsPanel.tsx` - Merkle 链验证
---
## 四、风险评估
### 高风险变更
| 变更 | 风险 | 缓解措施 |
|------|------|----------|
| Team Store API 集成 | API 失败导致数据丢失 | Feature flag 回退到 localStorage |
| 安全 Token 存储 | 认证中断 | 渐进迁移带回退 |
| TOML 解析器 | 配置损坏 | 写入前验证,保留备份 |
### 中等风险变更
| 变更 | 风险 | 缓解措施 |
|------|------|----------|
| REST 认证头 | 401 循环 | 智能重试带用户提示 |
| 配置同步 | 竞态条件 | 乐观锁,冲突 UI |
| 后端抽象 | 功能缺口 | 能力检测,优雅降级 |
---
## 五、成功度量
### Phase 0 完成标准
- [ ] Team CRUD 操作使用真实 API (通过网络请求验证)
- [ ] 所有 REST 请求包含认证头
- [ ] Workflow 编辑模式加载现有步骤
- [ ] Team 数据不再使用 localStorage (除缓存)
### Phase 1 完成标准
- [ ] 事件触发器可创建并正确触发
- [ ] 设置在应用重启后持久化
- [ ] 实时团队事件更新 UI
- [ ] Token 存储在安全存储中
### Phase 2 完成标准
- [ ] TOML 配置可读写
- [ ] 请求重试在瞬态故障时成功
- [ ] 后端可通过配置切换
- [ ] 配置变更双向同步
### Phase 3 完成标准
- [ ] 所有 16 层安全有 UI 展示
- [ ] Hand 审批工作流可用
- [ ] Hand 参数支持所有类型
- [ ] 审计日志可验证
### 总体指标
| 指标 | 当前 | 目标 |
|------|------|------|
| localStorage 使用 | 3 个文件 | 0 (除缓存) |
| API 集成 | ~70% | 100% |
| 实时事件 | 30% | 100% |
| 安全 UI 覆盖 | 20% | 100% |
| 测试覆盖率 | 未知 | 80%+ |
---
## 六、实施顺序
```
第 1-2 周: Phase 0
├── 0.1 Team Store API 集成 (3 天)
├── 0.2 REST API 认证 (2 天)
└── 0.3 Workflow 编辑器步骤加载 (2 天)
第 3-5 周: Phase 1
├── 1.1 事件触发器创建 (3 天)
├── 1.2 设置持久化 (2 天)
├── 1.3 WebSocket 事件订阅 (3 天)
└── 1.4 安全 Token 存储 (2 天)
第 6-8 周: Phase 2
├── 2.1 TOML 配置支持 (3 天)
├── 2.2 请求超时和重试 (2 天)
├── 2.3 后端抽象层 (3 天)
└── 2.4 配置同步服务 (2 天)
第 9-12 周: Phase 3
├── 3.1 16 层安全状态 UI (4 天)
├── 3.2 Hand 审批工作流 (3 天)
├── 3.3 增强 Hand 参数 UI (2 天)
└── 3.4 审计日志查看器 (3 天)
```
---
## 七、关键文件清单
### 需要修改的核心文件
| 文件 | 修改类型 | 优先级 |
|------|----------|--------|
| [desktop/src/store/teamStore.ts](desktop/src/store/teamStore.ts) | 替换 localStorage 为 API 调用 | P0 |
| [desktop/src/lib/team-client.ts](desktop/src/lib/team-client.ts) | 添加认证头和错误处理 | P0 |
| [desktop/src/lib/gateway-client.ts](desktop/src/lib/gateway-client.ts) | REST 认证模式参考 | P0 |
| [desktop/src/components/WorkflowEditor.tsx](desktop/src/components/WorkflowEditor.tsx) | 添加步骤加载 | P0 |
| [desktop/src/components/Settings/General.tsx](desktop/src/components/Settings/General.tsx) | 设置持久化 | P1 |
### 需要新建的文件
| 文件 | 用途 | 阶段 |
|------|------|------|
| `desktop/src/lib/config-client.ts` | 配置 API 客户端 | Phase 1 |
| `desktop/src/lib/toml-parser.ts` | TOML 解析工具 | Phase 2 |
| `desktop/src-tauri/src/secure_storage.rs` | 安全存储 Rust 命令 | Phase 1 |
| `desktop/src/components/CreateTriggerModal.tsx` | 触发器创建模态框 | Phase 1 |
---
## 八、验证方法
### 每个 Phase 完成后的验证
1. **自动化测试**
```bash
pnpm vitest run tests/desktop/
pnpm tsc --noEmit
```
2. **手动验证**
- 连接 OpenFang (端口 50051)
- 验证数据流真实连接
- 检查 localStorage 使用情况
- 验证设置持久化
3. **代码审查**
- 检查认证头存在
- 验证错误处理完整
- 确认无硬编码值
---
*计划创建: 2026-03-15*
*预计完成: 2026-06-15 (12 周)*