Files
zclaw_openfang/docs/features/audit-v12/M3-hands-system.md
iven 442ec0eeef
Some checks failed
CI / Lint & TypeCheck (push) Has been cancelled
CI / Unit Tests (push) Has been cancelled
CI / Build Frontend (push) Has been cancelled
CI / Rust Check (push) Has been cancelled
CI / Security Scan (push) Has been cancelled
CI / E2E Tests (push) Has been cancelled
docs(audit): V12 模块化端到端审计报告 — 11 模块 + 总报告
混合矩阵式审计:10 个功能模块 × 五维检查清单
- 项目整体健康度: 76/100
- 2 个 P0 (M4 双数据库 + 反思引擎 LLM 未接入)
- 15 个 P1 (跨 M2/M3/M4/M5/M6/M7/M11)
- 三类断链模式: 写了没接/接了不对/双实现未统一
- 三阶段修复路线图: P0(2-3天) → P1(5-7天) → P2(5-7天)
2026-04-04 17:55:03 +08:00

9.6 KiB
Raw Blame History

模块 M3 Hands 自主能力 审计报告

审计版本: V12 审计日期: 2026-04-04 审计范围: 11 个自主能力包触发/审批/执行/回调完整流程


1. 模块概况

功能描述

9 个已实现 HandBrowser/Researcher/Collector/Clip/Twitter/Whiteboard/Slideshow/Speech/Quiz含触发、审批、执行、事件回调全流程。

涉及文件清单

前端

  • Store: desktop/src/store/handStore.ts, desktop/src/store/browserHandStore.ts
  • Client: desktop/src/lib/kernel-hands.ts, desktop/src/lib/browser-client.ts
  • 自主管理: desktop/src/lib/autonomy-manager.ts
  • UI: desktop/src/components/Automation/ (ApprovalQueue, AutomationPanel, ExecutionResult 等)

后端 (Rust)

  • Tauri 命令: desktop/src-tauri/src/kernel_commands/hand.rs, approval.rs
  • Kernel: crates/zclaw-kernel/src/kernel/hands.rs, crates/zclaw-kernel/src/kernel/approvals.rs
  • Registry: crates/zclaw-hands/src/registry.rs
  • Hand 实现: crates/zclaw-hands/src/hands/ (9 个 .rs 文件)
  • 配置: hands/*.HAND.toml (9 个)

调用链路图

用户触发 Hand
  → AutomationPanel.triggerHand(id, params)
    → handStore.triggerHand()
      → canAutoExecute('hand_trigger', 5) [前端自主性检查]
      → client.triggerHand(name, params, autonomyLevel)
        → KernelClient.triggerHand() → invoke('hand_execute', { id, input, autonomyLevel })
          → Rust hand_execute:
            ├─ supervised 模式 → 创建 ApprovalEntry → 返回 pending_approval
            ├─ needs_approval + 非 autonomous → 创建 ApprovalEntry
            └─ autonomous 或无需审批 → kernel.execute_hand()
              → HandRegistry.execute() → Hand::execute()
              → 创建 HandRun (Pending→Running→Completed/Failed)
              → emit("hand-execution-complete")

审批流程:
  ApprovalQueue → handStore.respondToApproval()
    → invoke('approval_respond', { id, approved, reason })
      → kernel.respond_to_approval()
        → tokio::spawn 异步执行 Hand + 轮询完成
        → emit("hand-execution-complete")

前端事件接收:
  kernel-hands.ts onHandExecutionComplete → listen("hand-execution-complete")
    → [问题: 前端未注册全局监听]

2. 五维检查结果

2.1 链路完整性

链路 起点 终点 状态 备注
Hand 列举 AutomationPanel Registry.list() 连通
Hand 触发(直接执行) handStore Hand::execute() ⚠️ run_id 丢失 hand.rs:184 丢弃 _run_id
Hand 触发(需审批) handStore ApprovalEntry 连通
审批确认 ApprovalQueue Hand::execute() 连通 两条重复路径
hand-execution-complete 事件 Rust emit 前端 listen ⚠️ 无人接收 onHandExecutionComplete 未被调用
Browser Hand (Rust) BrowserHand::execute() 浏览器操作 断裂 只返回结构化指令不执行
Browser Hand (前端) browserHandStore browser-client → Rust browser_* 命令 连通 但绕过审批流程
Hand 取消 handStore cancel_flag AtomicBool 连通
Hand 运行状态查询 handStore Rust hand_run_status 连通

2.2 参数/类型一致性

接口 前端参数 后端参数 一致性 备注
hand_execute { id, input, autonomyLevel } id, input, autonomy_level camelCase 正确转换
hand_approve { handName, runId, approved, reason } hand_name, run_id, approved, reason
approval_respond { id, approved, reason } id, approved, reason
hand_execute 返回值 期望 { instance_id, status } 实际 { success, output, error, durationMs } 不匹配 前端拿不到 run_id
TOML permissions/rate_limit 定义了但未使用 HandConfig 只有基础字段 配置未生效

2.3 边界与错误处理

场景 预期行为 实际行为 级别
触发不存在的 Hand 返回错误 ZclawError::NotFound P4 正确
并发触发同一 Hand 限流/拒绝 无保护,可无限并发 P1
Hand 执行超时 超时终止 timeout_secs 定义但未使用 P1
审批不响应 超时清理 永不过期pending 无限积累 P2
Hand 执行失败 错误传播到 UI 错误传播链路完整 P4 正确
max_concurrent 限制 限制并发数 TOML 定义但未实现 P2
Clip Hand 路径含单引号 正常执行 ⚠️ FFmpeg concat 文件解析可能异常 P3

2.4 状态管理

Store/组件 状态机完整性 持久化 竞态风险
handStore idle/running/needs_approval/error/unavailable/setup_needed 无持久化 ⚠️ triggerHand 后依赖异步 loadHands 更新状态
browserHandStore sessions/execution/logs/templates 无持久化 ⚠️ 独立于 handStore绕过审批
autonomy-manager 三级自主+三级风险 localStorage 仅前端,后端无强制

2.5 安全与资源

检查项 状态 说明
审批安全(跨 Hand 攻击防护) entry.hand_id == hand_name 校验
Approval ID 不可预测 UUID v4
Browser Hand 绕过审批 P1 browserHandStore 完全绕过 autonomy-manager
TOML requires_approval 形同虚设 P1 browserHandStore 不走审批流程
审批内存不释放 ⚠️ P2 Vec 无限增长
Clip Hand 命令注入防护 使用 Command::new + .args() 非 shell

3. 问题清单

ID 描述 文件:行号 级别 修复建议 验证方法
M3-01 hand_execute 丢弃 run_id — 前端拿不到执行 ID无法追踪运行状态 hand.rs:184 P1 将 HandRunId 包含在返回结果中 triggerHand 后检查返回值含 runId
M3-02 Browser Hand 双路径断裂 — Rust execute() 只返回结构化指令不执行实际操作 browser.rs:191-343 P1 统一路径:要么 Rust 端执行操作,要么移除 Rust BrowserHand 通过 handStore 触发 browser 验证
M3-03 browserHandStore 绕过审批 — 无视 TOML requires_approval = true browserHandStore.ts:222-339 P1 browserHandStore 操作前检查 autonomy-manager 在 autonomous=false 下执行浏览器操作
M3-04 max_concurrent 未实现 — TOML 定义但运行时无检查 kernel/hands.rs P1 在 execute_hand 中添加并发计数检查 并发触发同一 Hand
M3-05 timeout_secs 未实现 — Hand 可无限挂起 hand.rs:47 P1 在 execute 中使用 tokio::time::timeout 包装 启动长时间 Hand 验证超时
M3-06 hand_execute 返回值类型不匹配 kernel-hands.ts:94 vs Rust HandResult P2 统一返回类型定义 检查 triggerHand 返回值
M3-07 hand-execution-complete 事件前端无人监听 kernel-hands.ts:195 P2 应用初始化时注册全局监听 审批执行完成后检查 UI 更新
M3-08 审批条目永不过期,内存不释放 approvals.rs:16-19 P2 添加 expires_at + 定期清理 检查长期运行后的 pending_approvals 大小
M3-09 重复审批确认路径hand_approve vs approval_respond hand.rs:196-295 vs approval.rs:54-142 P2 统一为单一审批路径 检查两路径是否行为一致
M3-10 tool_count/metric_count 硬编码为 0 hand.rs:82-83 P2 从 Hand 实际能力中计算 检查 hand_list 返回值
M3-11 TOML permissions/rate_limit/audit 配置未被读取 hands/*.HAND.toml vs hand.rs:10-32 P3 扩展 HandConfig 或在运行时解析 修改 TOML 验证行为无变化
M3-12 hand_trigger 在 autonomy-manager 中永远不自动允许 autonomy-manager.ts:268 P3 修正映射逻辑 设为 autonomous 后触发 Hand
M3-13 Clip Hand concat 文件路径单引号未转义 clip.rs:448 P3 转义路径中的单引号 使用含单引号的路径执行 concat

4. 改进建议

短期修复(按优先级)

  1. [P1] 修复 hand_execute 返回 run_id:在 HandResult 中添加 run_id 字段
  2. [P1] 统一 Browser Hand 路径:移除 Rust BrowserHand 的假执行,让 handStore 走 browserHandStore
  3. [P1] browserHandStore 集成审批流程:在 executeTemplate 前检查 autonomy-manager
  4. [P1] 实现 max_concurrent 并发限制
  5. [P1] 实现 timeout_secs 超时保护

长期架构建议

  • 注册 hand-execution-complete 全局监听器到 handStore
  • 统一审批路径(移除重复的 hand_approve / approval_respond
  • 添加审批 TTL 和自动清理
  • 扩展 HandConfig 解析 TOML 中的权限/限流/审计配置

5. 健康度评分

维度 评分 说明
链路完整性 55/100 Browser Hand 断裂、事件无人接收、run_id 丢失
参数一致性 70/100 invoke 参数匹配但返回值不匹配、TOML 配置未生效
边界处理 50/100 无并发限制、无超时、审批不过期
状态管理 60/100 基本状态机存在但 browserHandStore 独立运作
安全资源 55/100 Browser Hand 绕过审批是核心安全问题

综合健康度: 58/100

5 个 P1 级问题集中在此模块run_id 丢失、Browser 断裂、绕过审批、无并发限制、无超时)。修复 P1 后预计可提升至 75+。