Skill 菜单与展示优化¶
背景¶
Web 端 Skills 按钮在移动端存在多个严重问题:点击崩溃、菜单内容过时、技能数据为空。Dad 要求彻底修复交互问题并升级技能分类展示,最终推动了从前端 UI 修复到协议字段设计的完整演进。
2026-04-03:移动端 Skills 按钮崩溃修复¶
问题:手机视窗点击 Skills 按钮后页面 crash,触发 React Error #300(Rendered fewer hooks than expected)。
根因:组件内部存在 React Rules of Hooks 违规 —— 某些条件路径下 hook 数量不一致,点击 Skills 触发渲染分支变化导致崩溃。onOpenSlashMenu 本身只做 setInputValue('/') + setShowSlashMenu(true),并非直接原因。
解决:修复 SuggestionBar / ChatRoom 中条件 hook 调用问题,重新 build + deploy 后在手机视窗复测通过。
里程碑:移动端 Skills 按钮从"点击即崩"恢复为可用。
2026-04-03:斜杠命令菜单升级到 OpenClaw 2026.4.1¶
问题:Dad 反馈 Skills 按钮虽不崩溃了,但菜单内容仍是旧版命令集。
Dad 决策:要求按最新 OpenClaw 支持的 slash commands 更新菜单。
技术方案:前端 slash menu 改为按 section 分组展示,分为 4 组:
| Section | 命令示例 |
|---|---|
| COMMANDS | /help, /commands, /status, /whoami, /skill, /stop |
| SESSION | /new, /reset, /model |
| DIRECTIVES | 指令类命令 |
| ADVANCED | 高级命令 |
里程碑:斜杠菜单从单列表升级为 section 分组结构,对齐 OpenClaw 2026.4.1。
2026-04-03:Skills 数据为空 — 服务端扫描路径错误¶
问题:斜杠菜单中技能列表为空,之前有数据现在消失了。
根因:前端链路 agent.list → saveCachedAgents → getAgentInfo → agentInfo.skills 本身是通的,但 channel 插件只扫描 ~/.npm-global/lib/node_modules/openclaw/skills/,而 Owl 实际安装位置是 /usr/lib/node_modules/openclaw/skills/。
解决:扩展 scanInstalledSkills 的扫描路径,改为查找 OpenClaw 实际安装路径,不再硬编码单一目录。
里程碑:修复服务端 skills 扫描路径错误,恢复 agent.list 中 skills 数据来源。
2026-04-03:ChatRoom 未主动请求 agent.list¶
问题:服务端已能返回 skills,但客户端经常显示 skills: []。
根因:ChatRoom 在 connection.open 后只请求 selectAgent 和 requestHistory,不请求 requestAgentList。用户未经 ChatList 页面时,agentList 缓存为空。
解决:
- 在 connection.open 后自动请求 agent.list
- 收到响应后刷新 agentInfo
- ChatRoom 不再依赖 ChatList 预热缓存
结果:agentList 缓存成功建立,每个 agent 可拿到完整 skills(示例中 53 个),slash menu Skills 区域正常显示。
2026-04-04:技能分类展示需求 — 区分内置与已加载¶
Dad 决策:提出明确的展示层级要求: 1. 系统内置技能折叠起来 2. 只展示已加载的技能 3. 未加载技能灰色显示,放到最后 4. 斜杠消息点击后直接发送
第一次方案:channel 端拆分 skills 和 configuredSkills,前端用 skills - configuredSkills 推断 built-in。
问题:configuredSkills 实际已包含所有(user + npm),导致 skills == configuredSkills,built-in section 永远为空。
转折点:这是第一次把"技能分类展示"从前端 UI 问题升级为"协议字段设计问题"。
2026-04-04:Skills 按钮难以触发¶
问题:Dad 反馈"Skills 按钮要点好几遍才能点出来,有时候还不出来"。
解决:排查 SuggestionBar 与 onOpenSlashMenu 链路,修复 3 个相关问题 —— Skills 按钮触发链路、slash menu 打开条件、SuggestionBar 按钮显示逻辑。部署后触发稳定性显著提升。
2026-04-05:最终方案 — 显式 builtinSkills 字段¶
这是本主题最关键的结构化落地。
核心决策:不再靠前端差集推断 builtin,由 channel 插件显式提供 builtinSkills 字段。
实施步骤:
1. Channel 插件在 agent entry 构建时新增 builtinSkills 字段
2. 前端 AgentInfo 类型更新,支持 builtinSkills
3. ChatRoom.tsx 技能展示逻辑重构,基于明确字段分类
字段演进:
// 阶段一
skills: string[]
configuredSkills: string[]
// 阶段二(最终)
skills: string[]
configuredSkills: string[]
builtinSkills: string[] // 新增
展示逻辑:
- configuredSkills → 优先展示,已加载技能
- builtinSkills → 系统内置,折叠展示
- 其余 → 灰色显示,放末尾
结果:channel repo type check 通过,client-web build 通过,已提交并部署到 Owl。
里程碑:前端从"推断分类"升级为"显式字段驱动"的技能分类展示。
关键决策总览¶
| 时间 | 决策者 | 决策 |
|---|---|---|
| 04-03 09:03 | Dad | slash menu 必须对齐最新 OpenClaw 命令集 |
| 04-03 10:51 | Bot | skills 缺失定位为服务端扫描路径问题 |
| 04-03 22:57 | Bot | ChatRoom 技能缺失因未请求 agent.list |
| 04-04 21:27 | Dad | 内置技能折叠、已加载优先、未加载灰显 |
| 04-04 21:32 | Bot | 引入 configuredSkills 概念(首次尝试) |
| 04-05 13:42 | Bot | 新增 builtinSkills,放弃前端差集推断 |
最终状态¶
截至 2026-04-05 13:45,完整闭环:
- ✅ Skills 按钮崩溃修复(React Hooks 违规)
- ✅ Skills 按钮触发稳定性修复
- ✅ Slash menu 对齐 OpenClaw 2026.4.1 命令集
- ✅ ChatRoom 主动拉取 agent.list,skills 不依赖缓存
- ✅ Channel 插件新增 builtinSkills 字段
- ✅ 前端区分 builtinSkills / configuredSkills 展示
- ✅ 技能分类从"推断"升级为"显式字段驱动"