07 多 Harness 适配:同一套技能的多种方言¶
一、为什么一个方法论要支持多个宿主¶
Agent 生态的现实是:不同宿主有不同的插件目录、hook 生命周期、工具名称和用户交互 API。Superpowers 选择“同一套技能内容,多套薄适配层”,而不是为每个平台复制一份工作流。
flowchart TB
C[核心技能内容\nskills/*/SKILL.md]
C --> A[Claude plugin]
C --> B[Codex plugin]
C --> D[Cursor plugin]
C --> E[Gemini extension]
C --> F[Kimi plugin]
C --> G[OpenCode plugin]
C --> H[Pi extension]
A --> R1[宿主工具与 hook 方言]
B --> R2[宿主工具与 tool mapping]
D --> R3[additional_context]
E --> R4[GEMINI.md context]
F --> R5[AskUserQuestion / Agent / TodoList]
G --> R6[plugin bootstrap]
H --> R7[Pi extension API]
二、各平台入口的分工¶
| 平台 | 入口文件 | 主要作用 |
|---|---|---|
| Claude Code | .claude-plugin/plugin.json、.claude-plugin/marketplace.json |
声明插件身份、技能目录和市场信息 |
| Codex | .codex-plugin/plugin.json |
声明技能目录、能力、UI 元数据和默认 prompt |
| Cursor | .cursor-plugin/plugin.json、hooks/hooks-cursor.json |
复用技能目录并声明 Cursor hook |
| Gemini CLI | gemini-extension.json、GEMINI.md |
声明扩展和上下文文件 |
| Kimi Code | .kimi-plugin/plugin.json |
声明 session start skill 和工具映射文字 |
| OpenCode | .opencode/INSTALL.md、.opencode/plugins/superpowers.js |
通过插件脚本启动和加载技能 |
| Pi | .pi/extensions/superpowers.ts |
将技能流程接入 Pi extension API |
核心事实是:这些文件不是七套独立产品,而是七个入口适配器。它们都指向同一个 ./skills/,因此技能正文更新一次即可被多个宿主复用。
三、Claude/Cursor/Copilot 的 hook transport¶
hooks/session-start 用环境变量判断当前宿主并选择 JSON 字段,这种做法属于运行时适配。它不把宿主判断写进技能正文,避免在每个工作流章节都出现平台分支。
共享内容:<EXTREMELY-IMPORTANT> + using-superpowers 正文
平台差异:additional_context / hookSpecificOutput / additionalContext
这种“内容固定、封装变化”的结构特别适合 hook,因为平台差异集中在输出协议,不会污染业务逻辑。
四、Codex 与 Kimi:工具映射写成适配说明¶
.codex-plugin/plugin.json 的 skills 字段直接指向 ./skills/,而 Kimi manifest 还包含一段 skillInstructions,明确把 Superpowers 里常见的抽象映射到 Kimi 的原生工具:
| Superpowers 抽象 | Kimi 工具 |
|---|---|
| Ask user / multiple choice | AskUserQuestion |
| TodoWrite | TodoList |
| Task / general-purpose subagent | Agent,并按场景使用 coder/explore/plan |
| Read / search / fetch | Read、Grep、Glob、FetchURL |
| Skill tool | Kimi 原生 Skill |
这类映射没有改写核心 Skill,而是为宿主补一份“翻译词典”。当核心技能说“调用 Task tool”时,Kimi Agent 可以从词典知道应调用哪个工具和 subagent 类型。
五、OpenCode 与 Pi:从声明到代码桥接¶
OpenCode 和 Pi 不只靠 JSON manifest,还提供 JS/TS extension:
.opencode/plugins/superpowers.js负责在 OpenCode 的插件生命周期中加载或暴露技能;.pi/extensions/superpowers.ts负责把技能能力接入 Pi 的 extension API。
与静态 manifest 相比,代码桥接可以处理更复杂的初始化、事件监听和工具调用,但也带来更多测试负担。仓库因此有 tests/opencode/ 和 tests/pi/,分别检查插件加载、工具、优先级以及 Pi extension 行为。
六、适配层不应该承担什么¶
一个健康的适配层不应该:
- 复制一份
brainstorming或 TDD 正文; - 为某个平台改变核心流程的停止条件;
- 在多个入口中各自维护版本号和技能清单;
- 把宿主工具名称泄漏到通用方法论中。
它应该只承担:入口声明、字段转换、工具映射、平台特有初始化以及测试。
七、版本一致性是跨平台的隐性问题¶
多个 manifest 都包含 6.2.0,这带来一个维护风险:如果只更新部分文件,用户可能通过不同平台安装到不同版本标识。源码中的版本 bump 和同步脚本正是为了解决这类一致性问题,第 8 章会继续展开。
八、移植新 Harness 的建议顺序¶
不要一开始就重写所有技能。推荐顺序是:
- 先让宿主能加载
skills/; - 再让
using-superpowers在新会话出现; - 验证一个交互技能(brainstorming)和一个实现技能(TDD);
- 补工具名、用户提问和 subagent 的映射;
- 最后补平台加载、hook 和集成测试。
这样可以把“技能内容问题”和“宿主桥接问题”分开定位。
小结¶
多 Harness 适配的关键不是让所有平台内部完全相同,而是把稳定的高层过程与变化的低层方言分开。Superpowers 用共享 skills/ 保持方法论一致,用 manifest、hook、JS/TS extension 和工具映射吸收平台差异。