@zyaiting/keelson 0.4.0 → 0.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +48 -30
- package/README_CN.md +48 -30
- package/hooks/codebuddy-session.mjs +13 -28
- package/hooks/codex-session.mjs +16 -0
- package/hooks/prompt-state.mjs +5 -29
- package/hooks/session-start.mjs +7 -0
- package/hooks/workflow-guard.mjs +95 -0
- package/package.json +1 -1
- package/registry/platforms.json +4 -4
- package/registry/runtime-hashes.json +41 -0
- package/skills/keelson/SKILL.md +6 -3
- package/skills/keelson/references/build.md +12 -0
- package/skills/keelson/references/discover.md +5 -3
- package/skills/keelson/references/frontend.md +1 -1
- package/skills/keelson/references/interview.md +26 -7
- package/skills/keelson/references/land.md +2 -0
- package/skills/keelson/references/shape.md +3 -3
- package/skills/keelson/references/verify.md +1 -1
- package/skills/keelson/templates/resident-block.md +1 -1
- package/skills/keelson/templates/workflow.md +3 -3
- package/skills/zh/keelson/SKILL.md +6 -3
- package/skills/zh/keelson/references/build.md +12 -0
- package/skills/zh/keelson/references/discover.md +5 -3
- package/skills/zh/keelson/references/frontend.md +1 -1
- package/skills/zh/keelson/references/interview.md +26 -7
- package/skills/zh/keelson/references/land.md +2 -0
- package/skills/zh/keelson/references/shape.md +3 -3
- package/skills/zh/keelson/references/verify.md +2 -0
- package/skills/zh/keelson/templates/resident-block.md +1 -1
- package/skills/zh/keelson/templates/workflow.md +3 -3
- package/src/cli.js +4 -3
- package/src/commands/ablate.js +2 -1
- package/src/commands/ask.js +4 -1
- package/src/commands/context.js +7 -0
- package/src/commands/doctor.js +3 -1
- package/src/commands/hook.js +6 -1
- package/src/commands/init.js +12 -7
- package/src/commands/new.js +1 -1
- package/src/commands/platforms.js +1 -1
- package/src/commands/start.js +33 -0
- package/src/commands/uninstall.js +1 -1
- package/src/lib/decisions.js +3 -1
- package/src/lib/hook-context.js +30 -0
- package/src/lib/markdown.js +1 -1
- package/src/lib/rules.js +10 -2
- package/src/lib/workflow.js +102 -0
- package/src/platforms/integration.js +75 -93
- package/src/platforms/runtime.js +68 -17
package/README.md
CHANGED
|
@@ -1,33 +1,40 @@
|
|
|
1
1
|
<p align="center"><img src="https://raw.githubusercontent.com/Atingaii/keelson/main/docs/assets/keelson-banner.png" alt="Keelson" width="620"></p>
|
|
2
2
|
|
|
3
|
-
<p align="center"><strong>
|
|
3
|
+
<p align="center"><strong>Clarify the goal. Build to the contract. Keep what you learn.</strong></p>
|
|
4
4
|
<p align="center">Project memory, engineering guidance, and acceptance checks for your coding agent. Describe the outcome; keep decisions and verification alongside the code.</p>
|
|
5
5
|
|
|
6
6
|
<p align="center">
|
|
7
|
-
<a href="README_CN.md">简体中文</a> ·
|
|
7
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/README_CN.md">简体中文</a> ·
|
|
8
8
|
<a href="#quick-start">Quick start</a> ·
|
|
9
|
-
<a href="docs/README.md">Documentation</a> ·
|
|
10
|
-
<a href="docs/platforms.md">Agent support</a>
|
|
9
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/docs/README.md">Documentation</a> ·
|
|
10
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/docs/platforms.md">Agent support</a>
|
|
11
11
|
</p>
|
|
12
12
|
|
|
13
13
|
<p align="center">
|
|
14
|
+
<a href="https://www.npmjs.com/package/@zyaiting/keelson"><img src="https://img.shields.io/npm/v/%40zyaiting%2Fkeelson" alt="npm version"></a>
|
|
14
15
|
<a href="https://github.com/Atingaii/keelson/actions/workflows/ci.yml"><img src="https://github.com/Atingaii/keelson/actions/workflows/ci.yml/badge.svg?branch=main" alt="CI"></a>
|
|
15
|
-
<a href="LICENSE"><img src="https://img.shields.io/badge/License-MIT-blue.svg" alt="MIT license"></a>
|
|
16
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/LICENSE"><img src="https://img.shields.io/badge/License-MIT-blue.svg" alt="MIT license"></a>
|
|
16
17
|
</p>
|
|
17
18
|
|
|
18
|
-
<p align="center"><img src="https://raw.githubusercontent.com/Atingaii/keelson/main/docs/assets/keelson-demo.gif" alt="Real agent conversation replay: a task-filter request followed by implementation, verification, and archiving" width="100%"></p>
|
|
19
|
-
<p align="center"><sub>Initialized example repository · Translated excerpts from a real session, with waits shortened · Just describe the task</sub></p>
|
|
20
|
-
|
|
21
19
|
## Why Keelson?
|
|
22
20
|
|
|
23
|
-
|
|
21
|
+
Keelson brings software engineering practices into everyday agent conversations: agree on the outcome, preserve the reasoning, and check the result. It addresses four recurring problems.
|
|
24
22
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
23
|
+
**1. The agent builds the wrong thing.**
|
|
24
|
+
|
|
25
|
+
“Add a filter” leaves room for different defaults, edge cases, and compatibility choices. Keelson guides the agent to inspect the code, automatically investigate unclear goals and connected decisions, then turn the request into concrete acceptance examples before implementation. This applies **behaviour-driven development**: use examples to expose disagreement early, asking only about choices that affect the direction.
|
|
26
|
+
|
|
27
|
+
**2. Every session needs the same explanation.**
|
|
28
|
+
|
|
29
|
+
The next agent sees the code but may miss what “member” means or why an alternative was rejected. Keelson keeps domain terms, decisions, and unfinished work alongside the code. **Ubiquitous language** and **decision records** give later sessions shared vocabulary and reasons to work from, reducing repeated explanations.
|
|
30
|
+
|
|
31
|
+
**3. “Done” does not say what was checked.**
|
|
32
|
+
|
|
33
|
+
A passing test can miss the requested behaviour; an old result can describe old code. Keelson guides small implementation steps and acceptance review, and ties check records to the inputs they verified. **Short feedback loops** become a concrete completion gate: missing or stale verification blocks normal archiving.
|
|
34
|
+
|
|
35
|
+
**4. The page works, but using it feels rough.**
|
|
36
|
+
|
|
37
|
+
Unclear feedback, lost form input, and awkward mobile controls are usability problems. Keelson turns **usability heuristics** into guidance for hierarchy, interaction, responsive behaviour, and accessibility. The agent reviews the actual interface in a browser and checks real interactions, alongside code checks.
|
|
31
38
|
|
|
32
39
|
Keelson combines an **Agent Skill + local CLI**. The skill guides the agent's work; the CLI manages project state and verification records. Use it for features, bug fixes, refactoring, and frontend improvements.
|
|
33
40
|
|
|
@@ -37,7 +44,7 @@ Keelson combines an **Agent Skill + local CLI**. The skill guides the agent's wo
|
|
|
37
44
|
- A coding agent that can read project files, make changes, and run commands.
|
|
38
45
|
- A local project directory; Git is recommended for tracking code and project knowledge.
|
|
39
46
|
|
|
40
|
-
|
|
47
|
+
Claude Code, Codex CLI and CodeBuddy CLI are the primary supported hosts. Keelson also generates integrations for other coding agents. See [Agent support](https://github.com/Atingaii/keelson/blob/main/docs/platforms.md) for capabilities and validation coverage.
|
|
41
48
|
|
|
42
49
|
## Quick start
|
|
43
50
|
|
|
@@ -47,24 +54,30 @@ Keelson generates integrations for Codex, Claude Code, OpenCode, Gemini CLI, and
|
|
|
47
54
|
npm install -g @zyaiting/keelson
|
|
48
55
|
```
|
|
49
56
|
|
|
50
|
-
**2. Initialize your project**,
|
|
57
|
+
**2. Initialize your project**, selecting your CLI:
|
|
51
58
|
|
|
52
59
|
```bash
|
|
53
60
|
cd /path/to/your/project
|
|
54
|
-
keelson init --
|
|
61
|
+
keelson init --claude # Claude Code
|
|
62
|
+
# or: keelson init --codex
|
|
63
|
+
# or: keelson init --codebuddy
|
|
55
64
|
```
|
|
56
65
|
|
|
57
66
|
**3. Open your agent in that directory and describe the task.** Initialize once, then keep working through conversation.
|
|
58
67
|
|
|
59
|
-
> Add a priority filter to the task list
|
|
68
|
+
> Add a priority filter to the task list.
|
|
60
69
|
|
|
61
|
-
To upgrade, run `npm install -g @zyaiting/keelson@latest`, then `keelson update` in your project. See the [setup guide](docs/getting-started.md) and [supported agents](docs/platforms.md).
|
|
70
|
+
To upgrade, run `npm install -g @zyaiting/keelson@latest`, then `keelson update` in your project. See the [setup guide](https://github.com/Atingaii/keelson/blob/main/docs/getting-started.md) and [supported agents](https://github.com/Atingaii/keelson/blob/main/docs/platforms.md).
|
|
62
71
|
|
|
63
72
|
## From request to completion
|
|
64
73
|
|
|
65
|
-
**
|
|
74
|
+
**Investigate → Decide → Implement → Independently review → Verify → Preserve knowledge**
|
|
75
|
+
|
|
76
|
+
After initialization, ordinary requests trigger the relevant workflow automatically: investigate requirements, clarify material choices with recommendations, apply engineering and UI/UX guidance, implement, verify, and preserve the result for later sessions. You do not need to name a skill or manage workflow commands. Clear edits use a minimal change record. A simple gap gets one question; connected uncertainties get the whole ready decision frontier, with recommendations and reasons for each choice. The agent resumes authorized work once those choices are settled.
|
|
66
77
|
|
|
67
|
-
|
|
78
|
+
Before implementation, the agent starts the settled change and loads its declared specs and rules. Review gets a separate context pack built from the request and contracts. Verified changes promote durable decisions into project specs, so later work starts with what the project has learned.
|
|
79
|
+
|
|
80
|
+
Claude Code, Codex and CodeBuddy integrations restore workflow context and gate supported file edits. Codex requires the generated hooks to be trusted in `/hooks` when prompted; other host permissions remain in effect. Disabled hooks fall back to installed guidance and the shared CLI. See [automation and its boundaries](https://github.com/Atingaii/keelson/blob/main/docs/automation.md).
|
|
68
81
|
|
|
69
82
|
You can also ask:
|
|
70
83
|
|
|
@@ -72,7 +85,7 @@ You can also ask:
|
|
|
72
85
|
- **Improve an interface:** “Polish the settings page, keep our brand, preserve input when saving fails, and check the mobile flow.”
|
|
73
86
|
- **Resume:** “Continue the previous change. First check what's left.”
|
|
74
87
|
|
|
75
|
-
|
|
88
|
+
The agent automatically selects from 22 composable [design actions](https://github.com/Atingaii/keelson/blob/main/docs/frontend.md), discoverable with `keelson design`, including critique, simplification, polish, and adaptation when the work affects an interface. Checking the actual interface requires the agent to use a browser.
|
|
76
89
|
|
|
77
90
|
## What stays in your project?
|
|
78
91
|
|
|
@@ -85,17 +98,22 @@ Initialization creates a small foundation. Further documents appear as the work
|
|
|
85
98
|
| `.keelson/changes/`, `.keelson/specs/`, `.keelson/rules/` | Changes, behavior contracts, and project rules created as needed. |
|
|
86
99
|
| Host entry points such as `AGENTS.md` | Direct the agent to Keelson. |
|
|
87
100
|
|
|
88
|
-
Guidance comes from the installed package by default. Use `--vendor` when you want to commit a copy alongside your project. See [configuration](docs/configuration.md) for paths and options.
|
|
101
|
+
Guidance comes from the installed package by default. Use `--vendor` when you want to commit a copy alongside your project. See [configuration](https://github.com/Atingaii/keelson/blob/main/docs/configuration.md) for paths and options.
|
|
89
102
|
|
|
90
103
|
## Engineering principles
|
|
91
104
|
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
105
|
+
The ideas above come from established engineering and interaction design practices. Keelson adapts them to repository work:
|
|
106
|
+
|
|
107
|
+
| Principle | How it appears in Keelson |
|
|
108
|
+
| --- | --- |
|
|
109
|
+
| [Behaviour-driven development](https://cucumber.io/docs/bdd/) | Describe observable behaviour with acceptance examples; use them to guide implementation and review. |
|
|
110
|
+
| [Ubiquitous language](https://martinfowler.com/bliki/UbiquitousLanguage.html), from domain-driven design | Keep project terms and code-name mappings in a glossary as needed, so conversation and code use the same meanings. |
|
|
111
|
+
| [Architecture decision records](https://cognitect.com/blog/2011/11/15/documenting-architecture-decisions) | Keep concise decisions and trade-offs in the repository, with their context available to the next session. |
|
|
112
|
+
| [Small iterations and feedback](https://agilemanifesto.org/principles.html) | Build a working slice, check it, and adjust; keep small changes lightweight and add planning when complexity warrants it. |
|
|
113
|
+
| [Usability heuristics](https://www.nngroup.com/articles/ten-usability-heuristics/) | Review visible status, consistent language, error recovery, and user control through actual interface interactions. |
|
|
96
114
|
|
|
97
|
-
Review commands in `.keelson/config.yaml` before their first execution. The agent runs and records checks with `keelson check --trust --record`; passing exit codes still need an acceptance review. See [verification and trust](docs/verification.md).
|
|
115
|
+
Review commands in `.keelson/config.yaml` before their first execution. The agent runs and records checks with `keelson check --trust --record`; passing exit codes still need an acceptance review. See [verification and trust](https://github.com/Atingaii/keelson/blob/main/docs/verification.md).
|
|
98
116
|
|
|
99
117
|
## Documentation and contributing
|
|
100
118
|
|
|
101
|
-
[Documentation](docs/README.md) · [CLI reference](docs/cli.md) · [Frontend design](docs/frontend.md) · [Contributing](CONTRIBUTING.md) · [Report an issue](https://github.com/Atingaii/keelson/issues) · [MIT](LICENSE)
|
|
119
|
+
[Documentation](https://github.com/Atingaii/keelson/blob/main/docs/README.md) · [CLI reference](https://github.com/Atingaii/keelson/blob/main/docs/cli.md) · [Frontend design](https://github.com/Atingaii/keelson/blob/main/docs/frontend.md) · [Contributing](https://github.com/Atingaii/keelson/blob/main/CONTRIBUTING.md) · [Report an issue](https://github.com/Atingaii/keelson/issues) · [MIT](https://github.com/Atingaii/keelson/blob/main/LICENSE)
|
package/README_CN.md
CHANGED
|
@@ -1,33 +1,40 @@
|
|
|
1
1
|
<p align="center"><img src="https://raw.githubusercontent.com/Atingaii/keelson/main/docs/assets/keelson-banner.png" alt="Keelson" width="620"></p>
|
|
2
2
|
|
|
3
|
-
<p align="center"><strong
|
|
3
|
+
<p align="center"><strong>让 Agent 先想清楚,再按规范做完,把经验留在仓库。</strong></p>
|
|
4
4
|
<p align="center">为编码 Agent 提供项目记忆、工程方法和验收流程。你描述目标,Agent 推进实现,把决策与验证留在代码旁。</p>
|
|
5
5
|
|
|
6
6
|
<p align="center">
|
|
7
|
-
<a href="README.md">English</a> ·
|
|
7
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/README.md">English</a> ·
|
|
8
8
|
<a href="#快速开始">快速开始</a> ·
|
|
9
|
-
<a href="docs/zh/README.md">文档</a> ·
|
|
10
|
-
<a href="docs/platforms.md">Agent 支持</a>
|
|
9
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/docs/zh/README.md">文档</a> ·
|
|
10
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/docs/platforms.md">Agent 支持</a>
|
|
11
11
|
</p>
|
|
12
12
|
|
|
13
13
|
<p align="center">
|
|
14
|
+
<a href="https://www.npmjs.com/package/@zyaiting/keelson"><img src="https://img.shields.io/npm/v/%40zyaiting%2Fkeelson" alt="npm 版本"></a>
|
|
14
15
|
<a href="https://github.com/Atingaii/keelson/actions/workflows/ci.yml"><img src="https://github.com/Atingaii/keelson/actions/workflows/ci.yml/badge.svg?branch=main" alt="CI"></a>
|
|
15
|
-
<a href="LICENSE"><img src="https://img.shields.io/badge/License-MIT-blue.svg" alt="MIT license"></a>
|
|
16
|
+
<a href="https://github.com/Atingaii/keelson/blob/main/LICENSE"><img src="https://img.shields.io/badge/License-MIT-blue.svg" alt="MIT license"></a>
|
|
16
17
|
</p>
|
|
17
18
|
|
|
18
|
-
<p align="center"><img src="https://raw.githubusercontent.com/Atingaii/keelson/main/docs/assets/keelson-demo-zh.gif" alt="真实 Agent 对话回放:用户提出任务筛选需求,Agent 完成实现、验证与归档" width="100%"></p>
|
|
19
|
-
<p align="center"><sub>已初始化的示例仓库 · 真实会话节选,等待已压缩 · 用户只需提出需求</sub></p>
|
|
20
|
-
|
|
21
19
|
## 为什么选择 Keelson?
|
|
22
20
|
|
|
23
|
-
|
|
21
|
+
Keelson 将软件工程中的成熟做法带进日常 Agent 对话:先对齐结果,留下决策依据,再检查实际产出。它围绕四个常见问题展开。
|
|
24
22
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
23
|
+
**1. Agent 做出来的,并不是你想要的。**
|
|
24
|
+
|
|
25
|
+
“加个筛选”背后,还有默认行为、边界情况和兼容性。Keelson 引导 Agent 先读代码,自动调查模糊目标和相互关联的选择,把需求变成具体的验收示例,再开始实现。这借鉴了**行为驱动开发(BDD)**:通过例子尽早发现理解偏差,只对影响方向的选择提问。
|
|
26
|
+
|
|
27
|
+
**2. 换个会话,又得解释同一个项目。**
|
|
28
|
+
|
|
29
|
+
新 Agent 看得到代码,却未必知道“成员”的业务含义,也不知道某个方案为什么被否决。Keelson 将领域术语、决策和未完成工作留在仓库。**统一语言**与**决策记录**让后续会话沿用已有词汇和理由,减少重复解释。
|
|
30
|
+
|
|
31
|
+
**3. 说“完成了”,却不知道验证了什么。**
|
|
32
|
+
|
|
33
|
+
测试通过可能没有覆盖原始需求,旧结果也可能对应旧代码。Keelson 引导小步实现、逐项验收,并将检查记录绑定到受检输入。**短反馈循环**由此落实到完成条件:验证缺失或过期时,正常归档会被阻止。
|
|
34
|
+
|
|
35
|
+
**4. 页面能用,但用起来不顺手。**
|
|
36
|
+
|
|
37
|
+
反馈不清楚、保存失败丢输入、手机上操作别扭,都是可用性问题。Keelson 将**可用性启发式原则**转成层级、交互、响应式和无障碍指导,由 Agent 在浏览器中观察界面、实际操作,并结合代码检查验收。
|
|
31
38
|
|
|
32
39
|
Keelson 由 **Agent Skill + 本地 CLI** 组成:Skill 指导 Agent 如何工作,CLI 管理项目状态与验证记录。适用于新功能、问题修复、重构和前端体验优化。
|
|
33
40
|
|
|
@@ -37,7 +44,7 @@ Keelson 由 **Agent Skill + 本地 CLI** 组成:Skill 指导 Agent 如何工
|
|
|
37
44
|
- 一个能读取项目、修改文件并执行命令的编码 Agent。
|
|
38
45
|
- 一个本地项目目录;建议使用 Git 管理代码和项目知识。
|
|
39
46
|
|
|
40
|
-
|
|
47
|
+
重点适配 **Claude Code、Codex CLI 和 CodeBuddy CLI**,也支持其他编码 Agent 的集成入口;各宿主的能力与验证范围见 [Agent 支持](https://github.com/Atingaii/keelson/blob/main/docs/platforms.md)。
|
|
41
48
|
|
|
42
49
|
## 快速开始
|
|
43
50
|
|
|
@@ -47,24 +54,30 @@ Keelson 由 **Agent Skill + 本地 CLI** 组成:Skill 指导 Agent 如何工
|
|
|
47
54
|
npm install -g @zyaiting/keelson
|
|
48
55
|
```
|
|
49
56
|
|
|
50
|
-
**2.
|
|
57
|
+
**2. 在你的项目中初始化**,选择使用的 CLI:
|
|
51
58
|
|
|
52
59
|
```bash
|
|
53
60
|
cd /path/to/your/project
|
|
54
|
-
keelson init --
|
|
61
|
+
keelson init --claude --lang zh # Claude Code
|
|
62
|
+
# 或:keelson init --codex --lang zh
|
|
63
|
+
# 或:keelson init --codebuddy --lang zh
|
|
55
64
|
```
|
|
56
65
|
|
|
57
66
|
**3. 在这个目录启动 Agent,直接提出需求。** 初始化只需一次;后续正常对话即可。
|
|
58
67
|
|
|
59
|
-
>
|
|
68
|
+
> 给任务列表加一个优先级筛选。
|
|
60
69
|
|
|
61
|
-
升级 CLI:`npm install -g @zyaiting/keelson@latest`,然后在项目中运行 `keelson update`。更多设置见[上手教程](docs/zh/getting-started.md);其他宿主见 [Agent 支持](docs/platforms.md)。
|
|
70
|
+
升级 CLI:`npm install -g @zyaiting/keelson@latest`,然后在项目中运行 `keelson update`。更多设置见[上手教程](https://github.com/Atingaii/keelson/blob/main/docs/zh/getting-started.md);其他宿主见 [Agent 支持](https://github.com/Atingaii/keelson/blob/main/docs/platforms.md)。
|
|
62
71
|
|
|
63
72
|
## 从一句需求到一次完成
|
|
64
73
|
|
|
65
|
-
|
|
74
|
+
**调查 → 决策 → 实现 → 独立复核 → 验证 → 知识回写**
|
|
75
|
+
|
|
76
|
+
初始化后,普通需求自动触发相应流程:调查需求、带着推荐澄清关键选择、应用工程与 UI/UX 指导、实现、验证,并保留结果供后续会话接续。你无需点名 Skill 或管理工作流命令。明确的小修改使用最小变更记录;简单缺口一次问一个,复杂问题一轮问完前提已明确的整组决定,每题给推荐与理由。决定明确后继续已授权的工作。
|
|
66
77
|
|
|
67
|
-
Agent
|
|
78
|
+
实现前,Agent 自动启动已澄清的变更,加载声明的规范与规则;复核使用从原始需求和契约生成的独立上下文包。验收后,持久决策回写到项目规范,下次开发继续使用这些知识。
|
|
79
|
+
|
|
80
|
+
Claude Code、Codex 和 CodeBuddy 集成均支持恢复流程上下文,并对受支持的文件修改执行启动门禁。Codex 首次提示时需在 `/hooks` 中信任生成的 hooks;各宿主原有权限确认继续生效。禁用 hooks 时,由已安装指导驱动相同 CLI。详见[自动化机制与边界](https://github.com/Atingaii/keelson/blob/main/docs/zh/automation.md)。
|
|
68
81
|
|
|
69
82
|
你也可以这样说:
|
|
70
83
|
|
|
@@ -72,7 +85,7 @@ Agent 按任务读取需要的指导,维护验收标准并执行项目检查
|
|
|
72
85
|
- **改善界面:**“优化设置页,保留品牌风格,保存失败时不要丢输入,并检查手机端体验。”
|
|
73
86
|
- **接着开发:**“继续上次的改动,先确认还剩什么。”
|
|
74
87
|
|
|
75
|
-
|
|
88
|
+
涉及界面的任务中,Agent 会从 22 个可组合的[设计动作](https://github.com/Atingaii/keelson/blob/main/docs/zh/frontend.md)中按需选择,包括审视、简化、打磨和适配;可通过 `keelson design` 查看。实际界面效果需要 Agent 使用浏览器检查。
|
|
76
89
|
|
|
77
90
|
## 项目里会留下什么?
|
|
78
91
|
|
|
@@ -85,17 +98,22 @@ Agent 按任务读取需要的指导,维护验收标准并执行项目检查
|
|
|
85
98
|
| `.keelson/changes/`、`.keelson/specs/`、`.keelson/rules/` | 按需建立的变更、行为契约和项目规则。 |
|
|
86
99
|
| 宿主入口,如 `AGENTS.md` | 引导 Agent 加载 Keelson。 |
|
|
87
100
|
|
|
88
|
-
默认从已安装的包读取指导。需要把指导副本一并提交时,才使用 `--vendor`。目录与选项详见[配置文档](docs/zh/configuration.md)。
|
|
101
|
+
默认从已安装的包读取指导。需要把指导副本一并提交时,才使用 `--vendor`。目录与选项详见[配置文档](https://github.com/Atingaii/keelson/blob/main/docs/zh/configuration.md)。
|
|
89
102
|
|
|
90
103
|
## 工程学原理
|
|
91
104
|
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
105
|
+
前面的做法来自已有的软件工程与交互设计知识。Keelson 将它们用于仓库中的具体工作:
|
|
106
|
+
|
|
107
|
+
| 原理 | 在 Keelson 中如何落地 |
|
|
108
|
+
| --- | --- |
|
|
109
|
+
| [行为驱动开发(BDD)](https://cucumber.io/docs/bdd/) | 用验收示例描述可观察的行为,指导实现和需求核对。 |
|
|
110
|
+
| 领域驱动设计中的[统一语言](https://martinfowler.com/bliki/UbiquitousLanguage.html) | 按需记录业务术语及代码名称映射,让对话和代码中的词含义一致。 |
|
|
111
|
+
| [架构决策记录(ADR)](https://cognitect.com/blog/2011/11/15/documenting-architecture-decisions) | 在仓库保留简短决策与取舍,让后续会话理解当时的背景。 |
|
|
112
|
+
| [小步迭代与反馈](https://agilemanifesto.org/principles.html) | 先做出可工作的切片,检查后调整;小改动保持轻量,复杂时再补充计划。 |
|
|
113
|
+
| [可用性启发式原则](https://www.nngroup.com/articles/ten-usability-heuristics/) | 通过实际界面操作,检查状态是否可见、用词是否一致、错误能否恢复、用户能否掌控操作。 |
|
|
96
114
|
|
|
97
|
-
首次执行前应审阅 `.keelson/config.yaml` 中的检查命令。Agent 使用 `keelson check --trust --record` 运行并记录检查;退出码通过仍需对照验收标准。详见[验证与信任](docs/zh/verification.md)。
|
|
115
|
+
首次执行前应审阅 `.keelson/config.yaml` 中的检查命令。Agent 使用 `keelson check --trust --record` 运行并记录检查;退出码通过仍需对照验收标准。详见[验证与信任](https://github.com/Atingaii/keelson/blob/main/docs/zh/verification.md)。
|
|
98
116
|
|
|
99
117
|
## 文档与参与
|
|
100
118
|
|
|
101
|
-
[完整文档](docs/zh/README.md) · [命令参考](docs/zh/cli.md) · [前端设计](docs/zh/frontend.md) · [贡献指南](CONTRIBUTING.md) · [反馈问题](https://github.com/Atingaii/keelson/issues) · [MIT](LICENSE)
|
|
119
|
+
[完整文档](https://github.com/Atingaii/keelson/blob/main/docs/zh/README.md) · [命令参考](https://github.com/Atingaii/keelson/blob/main/docs/zh/cli.md) · [前端设计](https://github.com/Atingaii/keelson/blob/main/docs/zh/frontend.md) · [贡献指南](https://github.com/Atingaii/keelson/blob/main/CONTRIBUTING.md) · [反馈问题](https://github.com/Atingaii/keelson/issues) · [MIT](https://github.com/Atingaii/keelson/blob/main/LICENSE)
|
|
@@ -1,16 +1,13 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
// CodeBuddy session bridge for Keelson.
|
|
3
|
-
// SessionStart/UserPromptSubmit:
|
|
3
|
+
// SessionStart/UserPromptSubmit: restore workflow and declared project contracts.
|
|
4
4
|
// PreToolUse(Bash|PowerShell): deterministically prepend KEELSON_SESSION_ID to the command.
|
|
5
5
|
// Raw CodeBuddy session ids are never written to disk.
|
|
6
|
-
import crypto from 'node:crypto';
|
|
7
6
|
import fs from 'node:fs';
|
|
8
|
-
import
|
|
9
|
-
import {
|
|
7
|
+
import { findProjectRoot } from '../src/lib/paths.js';
|
|
8
|
+
import { hookEnvironment, sessionContext } from '../src/lib/hook-context.js';
|
|
9
|
+
import { writeSession } from '../src/lib/session.js';
|
|
10
10
|
|
|
11
|
-
const hash = (value, n) => crypto.createHash('sha256').update(String(value)).digest('hex').slice(0, n);
|
|
12
|
-
const readJson = (p) => { try { return JSON.parse(fs.readFileSync(p, 'utf8')); } catch { return null; } };
|
|
13
|
-
const writeJson = (p, v) => { fs.mkdirSync(path.dirname(p), { recursive: true }); fs.writeFileSync(p, JSON.stringify(v, null, 2) + '\n'); };
|
|
14
11
|
const shellQuote = (v) => `'${String(v).replace(/'/g, "'\\''")}'`;
|
|
15
12
|
|
|
16
13
|
let input = {};
|
|
@@ -19,17 +16,13 @@ try {
|
|
|
19
16
|
if (raw.trim()) input = JSON.parse(raw);
|
|
20
17
|
} catch {}
|
|
21
18
|
|
|
22
|
-
const root =
|
|
19
|
+
const root = findProjectRoot(process.env.CODEBUDDY_PROJECT_DIR || input.cwd || process.cwd());
|
|
23
20
|
const sessionId = typeof input.session_id === 'string' ? input.session_id.trim() : '';
|
|
24
|
-
if (!sessionId || !
|
|
21
|
+
if (!sessionId || !root) process.exit(0);
|
|
25
22
|
|
|
26
|
-
const
|
|
27
|
-
const
|
|
28
|
-
|
|
29
|
-
const session = readJson(sessionFile) || { schema: 1, change: null, createdAt: new Date().toISOString() };
|
|
30
|
-
session.updatedAt = new Date().toISOString();
|
|
31
|
-
session.source = 'codebuddy';
|
|
32
|
-
writeJson(sessionFile, session);
|
|
23
|
+
const env = hookEnvironment('codebuddy', input);
|
|
24
|
+
const opaque = env.KEELSON_SESSION_ID;
|
|
25
|
+
writeSession(root, { source: 'codebuddy' }, env);
|
|
33
26
|
|
|
34
27
|
const event = input.hook_event_name || '';
|
|
35
28
|
if (event === 'PreToolUse' && ['bash', 'powershell'].includes(String(input.tool_name || '').toLowerCase())) {
|
|
@@ -44,8 +37,6 @@ if (event === 'PreToolUse' && ['bash', 'powershell'].includes(String(input.tool_
|
|
|
44
37
|
continue: true,
|
|
45
38
|
hookSpecificOutput: {
|
|
46
39
|
hookEventName: 'PreToolUse',
|
|
47
|
-
permissionDecision: 'allow',
|
|
48
|
-
permissionDecisionReason: 'Keelson attached the opaque session identity used only for local work-focus routing.',
|
|
49
40
|
modifiedInput: {
|
|
50
41
|
...input.tool_input,
|
|
51
42
|
command: injected,
|
|
@@ -55,13 +46,7 @@ if (event === 'PreToolUse' && ['bash', 'powershell'].includes(String(input.tool_
|
|
|
55
46
|
process.exit(0);
|
|
56
47
|
}
|
|
57
48
|
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
.map((d) => d.name)
|
|
63
|
-
: [];
|
|
64
|
-
const focused = session.change && active.includes(session.change) ? session.change : null;
|
|
65
|
-
if (focused) process.stdout.write(`[keelson] session focus: ${focused}; use the existing change unless the user requests an independent outcome.\n`);
|
|
66
|
-
else if (active.length === 1) process.stdout.write(`[keelson] resume candidate: ${active[0]}; bind only if this prompt continues that work.\n`);
|
|
67
|
-
else if (active.length > 1) process.stdout.write(`[keelson] active changes: ${active.join(', ')}; no session focus, so do not guess.\n`);
|
|
49
|
+
if (['SessionStart', 'UserPromptSubmit'].includes(event)) {
|
|
50
|
+
try { process.stdout.write(sessionContext(root, env, event, 'codebuddy') + '\n'); }
|
|
51
|
+
catch (error) { process.stdout.write(`[keelson] Context restoration needs attention: ${error.message}\n`); }
|
|
52
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import fs from 'node:fs';
|
|
3
|
+
import { findProjectRoot } from '../src/lib/paths.js';
|
|
4
|
+
import { hookEnvironment, sessionContext } from '../src/lib/hook-context.js';
|
|
5
|
+
|
|
6
|
+
let input = {};
|
|
7
|
+
try { input = JSON.parse(fs.readFileSync(0, 'utf8')); } catch { process.exit(0); }
|
|
8
|
+
const root = findProjectRoot(input.cwd || process.cwd());
|
|
9
|
+
if (!root) process.exit(0);
|
|
10
|
+
const event = input.hook_event_name || 'SessionStart';
|
|
11
|
+
try {
|
|
12
|
+
const context = sessionContext(root, hookEnvironment('codex', input), event, 'codex');
|
|
13
|
+
process.stdout.write(JSON.stringify({ hookSpecificOutput: { hookEventName: event, additionalContext: context } }) + '\n');
|
|
14
|
+
} catch (error) {
|
|
15
|
+
process.stdout.write(`[keelson] Context restoration needs attention: ${error.message}\n`);
|
|
16
|
+
}
|
package/hooks/prompt-state.mjs
CHANGED
|
@@ -5,10 +5,10 @@ import crypto from 'node:crypto';
|
|
|
5
5
|
import fs from 'node:fs';
|
|
6
6
|
import path from 'node:path';
|
|
7
7
|
import { runtimeDir } from '../src/lib/runtime-path.js';
|
|
8
|
+
import { workflowHint } from '../src/lib/workflow.js';
|
|
8
9
|
|
|
9
10
|
const root = process.env.CLAUDE_PROJECT_DIR || process.cwd();
|
|
10
11
|
const k = path.join(root, '.keelson');
|
|
11
|
-
const changesDir = path.join(k, 'changes');
|
|
12
12
|
if (!fs.existsSync(k)) process.exit(0);
|
|
13
13
|
|
|
14
14
|
const read = (p) => (fs.existsSync(p) ? fs.readFileSync(p, 'utf8').replace(/\r\n?/g, '\n') : '');
|
|
@@ -35,32 +35,8 @@ if (sessionPath) {
|
|
|
35
35
|
session.source = 'claude-prompt';
|
|
36
36
|
writeJson(sessionPath, session);
|
|
37
37
|
}
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
const change = read(path.join(dir, 'change.md'));
|
|
43
|
-
if (!change) return null;
|
|
44
|
-
const tasks = read(path.join(dir, 'tasks.md'));
|
|
45
|
-
const total = (tasks.match(/^\s*[-*]\s+\[[ xX]\]/gm) || []).length;
|
|
46
|
-
const done = (tasks.match(/^\s*[-*]\s+\[[xX]\]/gm) || []).length;
|
|
47
|
-
const ledger = read(path.join(dir, 'ledger.md'));
|
|
48
|
-
const verifies = [...ledger.matchAll(/^###\s+Verify:[\s\S]*?exit\s*(?:code)?\s*[:=]?\s*(\d+)/gim)];
|
|
49
|
-
const lastExit = verifies.length ? Number(verifies.at(-1)[1]) : null;
|
|
50
|
-
const explicit = (change.match(/^status:\s*([\w-]+)/m) || [])[1];
|
|
51
|
-
const verify = verifies.length ? (lastExit === 0 ? 'passed' : 'failed') : 'not-run';
|
|
52
|
-
const open = (change.match(/^##\s+Open questions?\s*\n([\s\S]*?)(?=^##\s|(?![\s\S]))/im) || [])[1] || '';
|
|
53
|
-
const openCount = (open.match(/^\s*[-*]\s+(?!…|none)/gim) || []).length;
|
|
54
|
-
return `${name} · ${explicit || (total ? (done < total ? 'in-progress' : 'awaiting verification') : 'in-progress')} · verify ${verify}${total ? ` · ${done}/${total} tasks` : ''}${openCount ? ` · ${openCount} open` : ''}`;
|
|
55
|
-
};
|
|
56
|
-
|
|
57
|
-
if (session?.change) {
|
|
58
|
-
const line = summarize(session.change);
|
|
59
|
-
if (line) process.stdout.write(`[keelson] focus: ${line}\n`);
|
|
60
|
-
process.exit(0);
|
|
38
|
+
try {
|
|
39
|
+
process.stdout.write(workflowHint(root, { ...process.env, ...(envIdentity ? { KEELSON_SESSION_ID: envIdentity } : {}) }) + '\n');
|
|
40
|
+
} catch (error) {
|
|
41
|
+
process.stdout.write(`[keelson] Cannot restore workflow: ${error.message}. Run keelson doctor before implementation.\n`);
|
|
61
42
|
}
|
|
62
|
-
|
|
63
|
-
const names = fs.readdirSync(changesDir, { withFileTypes: true })
|
|
64
|
-
.filter((d) => d.isDirectory() && d.name !== 'archive' && fs.existsSync(path.join(changesDir, d.name, 'change.md')))
|
|
65
|
-
.map((d) => d.name);
|
|
66
|
-
if (names.length === 1) process.stdout.write(`[keelson] resume candidate: ${summarize(names[0])}; bind only if this prompt continues that work\n`);
|
package/hooks/session-start.mjs
CHANGED
|
@@ -5,6 +5,7 @@ import crypto from 'node:crypto';
|
|
|
5
5
|
import fs from 'node:fs';
|
|
6
6
|
import path from 'node:path';
|
|
7
7
|
import { runtimeDir } from '../src/lib/runtime-path.js';
|
|
8
|
+
import { activeWorkflow, phaseContext, renderPhaseContext, workflowHint } from '../src/lib/workflow.js';
|
|
8
9
|
|
|
9
10
|
const root = process.env.CLAUDE_PROJECT_DIR || process.cwd();
|
|
10
11
|
const k = path.join(root, '.keelson');
|
|
@@ -57,6 +58,7 @@ if (sessionPath) {
|
|
|
57
58
|
session = readJson(sessionPath) || { schema: 1, change: null, createdAt: new Date().toISOString() };
|
|
58
59
|
session.updatedAt = new Date().toISOString();
|
|
59
60
|
session.source = 'claude-session-start';
|
|
61
|
+
session.injectedContexts = []; // compact/resume must restore previously injected constraints.
|
|
60
62
|
writeJson(sessionPath, session);
|
|
61
63
|
}
|
|
62
64
|
|
|
@@ -91,4 +93,9 @@ if (ordered.length) {
|
|
|
91
93
|
lines.push('', '--- Active work ---');
|
|
92
94
|
for (const c of ordered.slice(0, 6)) lines.push(`${c.name}${c.name === focused ? ' [focus]' : ''}: ${c.tier}${c.status ? `, ${c.status}` : ''}${c.total ? `, ${c.done}/${c.total} tasks` : ''}${c.owner ? `, ${c.owner}` : ''}`);
|
|
93
95
|
}
|
|
96
|
+
try {
|
|
97
|
+
const env = { ...process.env, ...(envIdentity ? { KEELSON_SESSION_ID: envIdentity } : {}) };
|
|
98
|
+
lines.push('', workflowHint(root, env));
|
|
99
|
+
if (focused) lines.push(renderPhaseContext(phaseContext(root, activeWorkflow(root, focused, env))));
|
|
100
|
+
} catch (error) { lines.push(`[keelson] Context restoration needs attention: ${error.message}`); }
|
|
94
101
|
process.stdout.write(lines.join('\n') + '\n');
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// Host-specific file-tool gates and phase context injection. Shell/MCP writers
|
|
3
|
+
// remain host-policy territory; this is a workflow guard, not a sandbox.
|
|
4
|
+
import crypto from 'node:crypto';
|
|
5
|
+
import fs from 'node:fs';
|
|
6
|
+
import path from 'node:path';
|
|
7
|
+
import { findProjectRoot } from '../src/lib/paths.js';
|
|
8
|
+
import { hookEnvironment } from '../src/lib/hook-context.js';
|
|
9
|
+
import { readSession, writeSession } from '../src/lib/session.js';
|
|
10
|
+
import { activeWorkflow, implementationBlockers, phaseContext, renderPhaseContext } from '../src/lib/workflow.js';
|
|
11
|
+
|
|
12
|
+
let input = {};
|
|
13
|
+
try { input = JSON.parse(fs.readFileSync(0, 'utf8')); } catch { process.exit(2); }
|
|
14
|
+
const host = process.argv[2] || 'claude';
|
|
15
|
+
const projectDir = host === 'claude' ? process.env.CLAUDE_PROJECT_DIR : host === 'codebuddy' ? process.env.CODEBUDDY_PROJECT_DIR : null;
|
|
16
|
+
const root = findProjectRoot(projectDir || input.cwd || process.cwd());
|
|
17
|
+
if (!root) process.exit(0);
|
|
18
|
+
const env = hookEnvironment(host, input);
|
|
19
|
+
const event = input.hook_event_name || 'PreToolUse';
|
|
20
|
+
const tool = input.tool_name;
|
|
21
|
+
const output = (fields) => process.stdout.write(JSON.stringify({ hookSpecificOutput: { hookEventName: event, ...fields } }) + '\n');
|
|
22
|
+
|
|
23
|
+
try {
|
|
24
|
+
const session = readSession(root, env);
|
|
25
|
+
const name = session.state?.change;
|
|
26
|
+
if (host === 'codex' && event === 'SubagentStart' && !name) {
|
|
27
|
+
// session_id is the root, not necessarily the spawning parent. Let the
|
|
28
|
+
// assigned task name its change rather than inheriting an unrelated focus.
|
|
29
|
+
output({ additionalContext: '[keelson] Preserve your assigned scope, including read-only work. If your task includes KEELSON_CHANGE=<name>, run `keelson focus <name>`, then `keelson context --phase check` for review or `--phase implement` for implementation before doing that work. Do not infer a task from the root session or sole repository candidate. Without a marker, keep discovery read-only; create or select a change only when the task explicitly requires implementation. These commands do not grant permission to edit.' });
|
|
30
|
+
process.exit(0);
|
|
31
|
+
}
|
|
32
|
+
const workflow = activeWorkflow(root, name, env);
|
|
33
|
+
// Never infer an unrelated session's change from the sole repository candidate.
|
|
34
|
+
if (!name) workflow.change = null;
|
|
35
|
+
const args = input.tool_input ?? {};
|
|
36
|
+
const file = args.file_path ?? args.notebook_path;
|
|
37
|
+
const patch = host === 'codex' && tool === 'apply_patch';
|
|
38
|
+
const editing = patch || ['Edit', 'Write', 'MultiEdit', 'NotebookEdit', 'NotebookWrite'].includes(tool);
|
|
39
|
+
const files = patch
|
|
40
|
+
? [...String(args.command ?? '').matchAll(/^\*\*\* (?:Add File|Update File|Delete File|Move to): (.+)\r?$/gm)].map((m) => m[1].trim())
|
|
41
|
+
: typeof file === 'string' ? [file] : [];
|
|
42
|
+
const relative = files.map((f) => path.relative(root, path.resolve(input.cwd || root, f)).replace(/\\/g, '/'));
|
|
43
|
+
const planningOnly = relative.length > 0 && relative.every((f) => f.startsWith('.keelson/') && !f.split('/').includes('..'));
|
|
44
|
+
if (editing && !planningOnly) {
|
|
45
|
+
const blockers = implementationBlockers(workflow.change, workflow.changes);
|
|
46
|
+
if (blockers.length) {
|
|
47
|
+
output({ permissionDecision: 'deny', permissionDecisionReason: blockers.join(' ') + ' The agent should resolve this within existing authorization; do not ask the user to run workflow commands.' });
|
|
48
|
+
process.exit(0);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
if (editing && planningOnly) process.exit(0);
|
|
52
|
+
if (!workflow.change) process.exit(0);
|
|
53
|
+
if (host === 'codex' && ['spawn_agent', 'Agent', 'Task'].includes(tool)) {
|
|
54
|
+
const markers = [...String(args.message ?? args.prompt ?? '').matchAll(/^\s*KEELSON_CHANGE=([^\s]+)[ \t]*$/gm)];
|
|
55
|
+
if (markers.length !== 1 || markers[0][1] !== name) {
|
|
56
|
+
output({ permissionDecision: 'deny', permissionDecisionReason: `Add the single line KEELSON_CHANGE=${name} to this child task so its own CLI session can bind the assigned change. Keep its phase, original instructions and any read-only scope. The agent should correct the task prompt; do not ask the user to run workflow commands.` });
|
|
57
|
+
process.exit(0);
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
const descriptor = `${input.agent_type ?? ''} ${args.subagent_type ?? args.agent_type ?? ''} ${args.description ?? ''} ${args.prompt ?? args.message ?? ''}`;
|
|
61
|
+
const reviewing = /KEELSON_PHASE=check|keelson-check|\breview\b|\breviewer\b|复核|审查/i.test(descriptor);
|
|
62
|
+
if (event === 'SubagentStart' && !reviewing && !/KEELSON_PHASE=implement|keelson-implement/i.test(descriptor)) {
|
|
63
|
+
// Generic agent_type carries no parent's prompt or reliable phase. The
|
|
64
|
+
// Agent/Task hook already injected the appropriate pack into that prompt.
|
|
65
|
+
const hint = '[keelson] Follow the phase and contracts in your task prompt. If they are missing, load `keelson context --phase check` for review or `--phase implement` for implementation. Preserve your assigned scope; context is not permission to edit.';
|
|
66
|
+
// A bound Codex child can safely receive its own packs. An unbound child
|
|
67
|
+
// received explicit binding instructions above, never a guessed root task.
|
|
68
|
+
const packs = host === 'codex' ? ['implement', 'check'].map((phase) => renderPhaseContext(phaseContext(root, workflow, phase))) : [];
|
|
69
|
+
output({ additionalContext: [hint, ...packs].join('\n\n') });
|
|
70
|
+
process.exit(0);
|
|
71
|
+
}
|
|
72
|
+
const phase = reviewing ? 'check' : 'implement';
|
|
73
|
+
const pack = phaseContext(root, workflow, phase, relative);
|
|
74
|
+
const context = renderPhaseContext(pack);
|
|
75
|
+
if (['Agent', 'Task'].includes(tool) && typeof args.prompt === 'string') {
|
|
76
|
+
// Preserve every original argument and normal host permission checks.
|
|
77
|
+
if (host === 'codex') output({ additionalContext: context });
|
|
78
|
+
else output({ [host === 'codebuddy' ? 'modifiedInput' : 'updatedInput']: { ...args, prompt: `${args.prompt}\n\n${context}` } });
|
|
79
|
+
} else if (event === 'SubagentStart') {
|
|
80
|
+
output({ additionalContext: context });
|
|
81
|
+
} else if (host === 'codex' && input.agent_id) {
|
|
82
|
+
// Codex does not emit SessionStart when a child compacts or resumes. Do
|
|
83
|
+
// not suppress the next contract pack on the basis of a pre-compact cache.
|
|
84
|
+
output({ additionalContext: context });
|
|
85
|
+
} else if (host !== 'codebuddy') {
|
|
86
|
+
const digest = crypto.createHash('sha256').update(`${input.agent_id ?? 'main'}\n${context}`).digest('hex');
|
|
87
|
+
if (!(session.state?.injectedContexts ?? []).includes(digest)) {
|
|
88
|
+
output({ additionalContext: context });
|
|
89
|
+
writeSession(root, { injectedContexts: [...(session.state?.injectedContexts ?? []).slice(-15), digest] }, env);
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
} catch (error) {
|
|
93
|
+
if (event === 'PreToolUse') output({ permissionDecision: 'deny', permissionDecisionReason: `Keelson context could not be loaded: ${error.message}. Repair the declared context before retrying.` });
|
|
94
|
+
else output({ additionalContext: `Keelson context could not be loaded: ${error.message}. Investigate before implementation.` });
|
|
95
|
+
}
|
package/package.json
CHANGED
package/registry/platforms.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 2,
|
|
3
|
-
"updated": "2026-09-
|
|
4
|
-
"note": "Adapters describe generated discovery paths, not a promise of live end-to-end host parity. Codex session identity has been exercised locally. Other hosts have adapter contract tests;
|
|
3
|
+
"updated": "2026-09-21",
|
|
4
|
+
"note": "Adapters describe generated discovery paths, not a promise of live end-to-end host parity. Codex session identity has been exercised locally. Other hosts have adapter contract tests; Claude Code, Codex and CodeBuddy have workflow hook adapters; hook execution depends on the host version, trust and settings. Native session identity sources include CODEX_THREAD_ID, Claude hooks, Pi environment and explicit KEELSON_SESSION_ID. No source means an honest degraded state. Default installation is lightweight; --vendor explicitly copies package guidance.",
|
|
5
5
|
"platforms": {
|
|
6
6
|
"claude": {
|
|
7
7
|
"label": "Claude Code",
|
|
@@ -19,7 +19,7 @@
|
|
|
19
19
|
"bin": "codex",
|
|
20
20
|
"instructions": "AGENTS.md",
|
|
21
21
|
"skillsDir": ".agents/skills",
|
|
22
|
-
"hooks":
|
|
22
|
+
"hooks": true,
|
|
23
23
|
"confidence": "verified",
|
|
24
24
|
"support": "first-class",
|
|
25
25
|
"sessionFocus": "native",
|
|
@@ -71,7 +71,7 @@
|
|
|
71
71
|
"bin": "codebuddy",
|
|
72
72
|
"instructions": "CODEBUDDY.md",
|
|
73
73
|
"skillsDir": ".codebuddy/skills",
|
|
74
|
-
"hooks":
|
|
74
|
+
"hooks": true,
|
|
75
75
|
"confidence": "documented",
|
|
76
76
|
"support": "first-class",
|
|
77
77
|
"sessionFocus": "native",
|