cclaw-cli 0.51.30 → 1.0.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 +24 -18
- package/dist/artifact-linter/brainstorm.d.ts +2 -0
- package/dist/artifact-linter/brainstorm.js +289 -0
- package/dist/artifact-linter/design.d.ts +2 -0
- package/dist/artifact-linter/design.js +354 -0
- package/dist/artifact-linter/plan.d.ts +2 -0
- package/dist/artifact-linter/plan.js +183 -0
- package/dist/artifact-linter/review-army.d.ts +24 -0
- package/dist/artifact-linter/review-army.js +365 -0
- package/dist/artifact-linter/review.d.ts +2 -0
- package/dist/artifact-linter/review.js +99 -0
- package/dist/artifact-linter/scope.d.ts +2 -0
- package/dist/artifact-linter/scope.js +125 -0
- package/dist/artifact-linter/shared.d.ts +247 -0
- package/dist/artifact-linter/shared.js +1517 -0
- package/dist/artifact-linter/ship.d.ts +2 -0
- package/dist/artifact-linter/ship.js +82 -0
- package/dist/artifact-linter/spec.d.ts +2 -0
- package/dist/artifact-linter/spec.js +130 -0
- package/dist/artifact-linter/tdd.d.ts +2 -0
- package/dist/artifact-linter/tdd.js +198 -0
- package/dist/artifact-linter.d.ts +4 -76
- package/dist/artifact-linter.js +56 -2949
- package/dist/cli.d.ts +1 -6
- package/dist/cli.js +4 -159
- package/dist/codex-feature-flag.d.ts +1 -1
- package/dist/codex-feature-flag.js +1 -1
- package/dist/config.d.ts +3 -2
- package/dist/config.js +67 -3
- package/dist/constants.d.ts +1 -7
- package/dist/constants.js +10 -15
- package/dist/content/cancel-command.js +2 -2
- package/dist/content/closeout-guidance.d.ts +1 -1
- package/dist/content/closeout-guidance.js +15 -13
- package/dist/content/core-agents.d.ts +46 -29
- package/dist/content/core-agents.js +216 -82
- package/dist/content/decision-protocol.d.ts +1 -1
- package/dist/content/decision-protocol.js +1 -1
- package/dist/content/diff-command.js +1 -1
- package/dist/content/examples.d.ts +0 -3
- package/dist/content/examples.js +197 -752
- package/dist/content/harness-doc.js +20 -2
- package/dist/content/hook-manifest.d.ts +2 -2
- package/dist/content/hook-manifest.js +2 -2
- package/dist/content/hooks.d.ts +1 -0
- package/dist/content/hooks.js +32 -137
- package/dist/content/idea.d.ts +60 -0
- package/dist/content/idea.js +404 -0
- package/dist/content/iron-laws.d.ts +0 -1
- package/dist/content/iron-laws.js +31 -16
- package/dist/content/learnings.d.ts +2 -4
- package/dist/content/learnings.js +11 -27
- package/dist/content/meta-skill.js +7 -7
- package/dist/content/node-hooks.d.ts +10 -0
- package/dist/content/node-hooks.js +163 -95
- package/dist/content/opencode-plugin.js +15 -29
- package/dist/content/reference-patterns.js +2 -2
- package/dist/content/runtime-shared-snippets.d.ts +8 -0
- package/dist/content/runtime-shared-snippets.js +80 -0
- package/dist/content/session-hooks.js +1 -1
- package/dist/content/skills.d.ts +1 -0
- package/dist/content/skills.js +69 -7
- package/dist/content/stage-schema.js +147 -61
- package/dist/content/stages/_lint-metadata/index.js +26 -2
- package/dist/content/stages/brainstorm.js +13 -7
- package/dist/content/stages/design.js +16 -11
- package/dist/content/stages/plan.js +7 -4
- package/dist/content/stages/review.js +12 -12
- package/dist/content/stages/schema-types.d.ts +2 -2
- package/dist/content/stages/scope.js +15 -12
- package/dist/content/stages/ship.js +3 -3
- package/dist/content/stages/spec.js +9 -3
- package/dist/content/stages/tdd.js +14 -4
- package/dist/content/start-command.js +11 -10
- package/dist/content/status-command.js +5 -5
- package/dist/content/subagent-context-skills.js +156 -1
- package/dist/content/subagents.d.ts +0 -5
- package/dist/content/subagents.js +65 -81
- package/dist/content/templates.d.ts +1 -1
- package/dist/content/templates.js +187 -154
- package/dist/content/tree-command.js +2 -2
- package/dist/content/utility-skills.d.ts +2 -2
- package/dist/content/utility-skills.js +28 -99
- package/dist/content/view-command.js +4 -2
- package/dist/delegation.d.ts +2 -0
- package/dist/delegation.js +2 -1
- package/dist/early-loop.d.ts +66 -0
- package/dist/early-loop.js +275 -0
- package/dist/flow-state.d.ts +5 -6
- package/dist/flow-state.js +4 -6
- package/dist/gate-evidence.d.ts +0 -23
- package/dist/gate-evidence.js +111 -153
- package/dist/harness-adapters.d.ts +2 -2
- package/dist/harness-adapters.js +48 -19
- package/dist/install.js +190 -32
- package/dist/internal/advance-stage/advance.d.ts +50 -0
- package/dist/internal/advance-stage/advance.js +479 -0
- package/dist/internal/advance-stage/cancel-run.d.ts +8 -0
- package/dist/internal/advance-stage/cancel-run.js +19 -0
- package/dist/internal/advance-stage/flow-state-coercion.d.ts +3 -0
- package/dist/internal/advance-stage/flow-state-coercion.js +81 -0
- package/dist/internal/advance-stage/helpers.d.ts +14 -0
- package/dist/internal/advance-stage/helpers.js +145 -0
- package/dist/internal/advance-stage/hook.d.ts +8 -0
- package/dist/internal/advance-stage/hook.js +40 -0
- package/dist/internal/advance-stage/parsers.d.ts +54 -0
- package/dist/internal/advance-stage/parsers.js +307 -0
- package/dist/internal/advance-stage/review-loop.d.ts +7 -0
- package/dist/internal/advance-stage/review-loop.js +161 -0
- package/dist/internal/advance-stage/rewind.d.ts +14 -0
- package/dist/internal/advance-stage/rewind.js +108 -0
- package/dist/internal/advance-stage/start-flow.d.ts +11 -0
- package/dist/internal/advance-stage/start-flow.js +136 -0
- package/dist/internal/advance-stage/verify.d.ts +29 -0
- package/dist/internal/advance-stage/verify.js +225 -0
- package/dist/internal/advance-stage.js +21 -1470
- package/dist/internal/compound-readiness.d.ts +1 -1
- package/dist/internal/compound-readiness.js +2 -2
- package/dist/internal/early-loop-status.d.ts +7 -0
- package/dist/internal/early-loop-status.js +90 -0
- package/dist/internal/runtime-integrity.d.ts +7 -0
- package/dist/internal/runtime-integrity.js +288 -0
- package/dist/internal/tdd-red-evidence.js +1 -1
- package/dist/knowledge-store.d.ts +5 -28
- package/dist/knowledge-store.js +57 -84
- package/dist/managed-resources.js +24 -2
- package/dist/policy.js +7 -9
- package/dist/retro-gate.js +8 -90
- package/dist/run-archive.d.ts +1 -1
- package/dist/run-archive.js +13 -16
- package/dist/run-persistence.js +20 -15
- package/dist/runtime/run-hook.entry.d.ts +3 -0
- package/dist/runtime/run-hook.entry.js +5 -0
- package/dist/runtime/run-hook.mjs +9477 -0
- package/dist/tdd-cycle.d.ts +3 -3
- package/dist/tdd-cycle.js +1 -1
- package/dist/types.d.ts +18 -10
- package/package.json +4 -2
- package/dist/content/hook-inline-snippets.d.ts +0 -83
- package/dist/content/hook-inline-snippets.js +0 -302
- package/dist/content/ideate-command.d.ts +0 -8
- package/dist/content/ideate-command.js +0 -315
- package/dist/content/ideate-frames.d.ts +0 -31
- package/dist/content/ideate-frames.js +0 -140
- package/dist/content/ideate-ranking.d.ts +0 -25
- package/dist/content/ideate-ranking.js +0 -65
- package/dist/content/next-command.d.ts +0 -20
- package/dist/content/next-command.js +0 -298
- package/dist/content/seed-shelf.d.ts +0 -36
- package/dist/content/seed-shelf.js +0 -301
- package/dist/content/stage-common-guidance.d.ts +0 -1
- package/dist/content/stage-common-guidance.js +0 -106
- package/dist/doctor-registry.d.ts +0 -10
- package/dist/doctor-registry.js +0 -186
- package/dist/doctor.d.ts +0 -17
- package/dist/doctor.js +0 -2201
- package/dist/internal/hook-manifest.d.ts +0 -16
- package/dist/internal/hook-manifest.js +0 -77
- package/dist/trace-matrix.d.ts +0 -27
- package/dist/trace-matrix.js +0 -226
|
@@ -1,315 +0,0 @@
|
|
|
1
|
-
import { RUNTIME_ROOT } from "../constants.js";
|
|
2
|
-
import { resolveIdeateFrames } from "./ideate-frames.js";
|
|
3
|
-
import { ideateStructuredAskToolsWithFallback } from "./decision-protocol.js";
|
|
4
|
-
import { conversationLanguagePolicyMarkdown } from "./language-policy.js";
|
|
5
|
-
const IDEATE_SKILL_FOLDER = "flow-ideate";
|
|
6
|
-
const IDEATE_SKILL_NAME = "flow-ideate";
|
|
7
|
-
/**
|
|
8
|
-
* Directory + filename convention for ideate artifacts. These are separate
|
|
9
|
-
* from stage artifacts (00-..08-*.md) because `/cc-ideate` runs outside the
|
|
10
|
-
* critical-path flow state machine and must not collide with stage numbering.
|
|
11
|
-
*/
|
|
12
|
-
const IDEATE_ARTIFACT_GLOB = ".cclaw/artifacts/ideate-*.md";
|
|
13
|
-
const IDEATE_ARTIFACT_PATTERN = ".cclaw/artifacts/ideate-<YYYY-MM-DD-slug>.md";
|
|
14
|
-
const IDEATE_RESUME_WINDOW_DAYS = 30;
|
|
15
|
-
const STRUCTURED_ASK_TOOLS = ideateStructuredAskToolsWithFallback();
|
|
16
|
-
export function minimumDistinctIdeateFrames(frameCount, mode = "repo-grounded") {
|
|
17
|
-
if (frameCount <= 0)
|
|
18
|
-
return 0;
|
|
19
|
-
const cap = mode === "repo-grounded" ? 4 : 2;
|
|
20
|
-
return Math.min(cap, frameCount);
|
|
21
|
-
}
|
|
22
|
-
function renderFrameBullets(frameIds) {
|
|
23
|
-
return resolveIdeateFrames(frameIds)
|
|
24
|
-
.map((frame) => ` - ${frame.label} (\`${frame.id}\`)`)
|
|
25
|
-
.join("\n");
|
|
26
|
-
}
|
|
27
|
-
function renderFrameNames(frameIds) {
|
|
28
|
-
return resolveIdeateFrames(frameIds)
|
|
29
|
-
.map((frame) => frame.label)
|
|
30
|
-
.join(", ");
|
|
31
|
-
}
|
|
32
|
-
export function ideateCommandContract(options = {}) {
|
|
33
|
-
const frames = resolveIdeateFrames(options.frameIds);
|
|
34
|
-
const frameBullets = renderFrameBullets(options.frameIds);
|
|
35
|
-
const minimumDistinctFrames = minimumDistinctIdeateFrames(frames.length, options.mode);
|
|
36
|
-
return `# /cc-ideate
|
|
37
|
-
|
|
38
|
-
## Purpose
|
|
39
|
-
|
|
40
|
-
Repository-improvement ideate mode. Generate a ranked backlog of
|
|
41
|
-
high-value improvements, persist it as an artifact on disk, and end with
|
|
42
|
-
an explicit handoff — either launch \`/cc\` on a chosen candidate in the
|
|
43
|
-
same session, or save/discard the backlog.
|
|
44
|
-
|
|
45
|
-
## HARD-GATE
|
|
46
|
-
|
|
47
|
-
${conversationLanguagePolicyMarkdown()}
|
|
48
|
-
- Ideate mode only. Never mutate \`.cclaw/state/flow-state.json\`.
|
|
49
|
-
- Every recommendation cites evidence from the current repository
|
|
50
|
-
(file path, command output, or knowledge-store entry id).
|
|
51
|
-
- Always write a persisted artifact to
|
|
52
|
-
\`${IDEATE_ARTIFACT_PATTERN}\`. Chat-only output is not acceptable —
|
|
53
|
-
the next session must be able to resume.
|
|
54
|
-
- Always end with a structured handoff prompt, not an open question.
|
|
55
|
-
|
|
56
|
-
## Algorithm
|
|
57
|
-
|
|
58
|
-
1. **Resume check.** Glob \`${IDEATE_ARTIFACT_GLOB}\`. If any artifact
|
|
59
|
-
has been modified within the last ${IDEATE_RESUME_WINDOW_DAYS} days,
|
|
60
|
-
offer the user: continue that backlog, start fresh, or cancel.
|
|
61
|
-
2. **Mode classification.** Explicitly classify subject:
|
|
62
|
-
\`repo-grounded\` / \`elsewhere-software\` / \`elsewhere-non-software\` / \`narrow\`.
|
|
63
|
-
Do not assume repo-grounded by default. Repo-grounded scans keep the
|
|
64
|
-
broadest frame minimum; narrow and non-repo modes use the smaller minimum
|
|
65
|
-
shown below.
|
|
66
|
-
3. **Mode-aware grounding (parallel).**
|
|
67
|
-
- Repo-grounded: repo signal scan + \`${RUNTIME_ROOT}/knowledge.jsonl\`
|
|
68
|
-
repetition scan.
|
|
69
|
-
- Elsewhere-software: docs-first grounding (Context7 and official docs).
|
|
70
|
-
- Elsewhere-non-software: constraints and objective grounding.
|
|
71
|
-
4. **Divergent ideation frames (parallel).** Generate candidates with
|
|
72
|
-
configured frames (${frames.length} total):
|
|
73
|
-
${frameBullets}
|
|
74
|
-
Keep at least ${minimumDistinctFrames} distinct frame outputs in this rendered mode.
|
|
75
|
-
Deterministic minimum: repo-grounded = 4, narrow/non-repo = 2, always capped
|
|
76
|
-
by configured frame count.
|
|
77
|
-
5. **Adversarial critique pass.** For each candidate, write the strongest
|
|
78
|
-
counter-argument, kill weak ideas, and keep survivors only.
|
|
79
|
-
6. **Produce 5-10 survivors** with impact (High/Medium/Low),
|
|
80
|
-
effort (S/M/L), confidence (High/Medium/Low), **why now**, expected user impact, risk, and one evidence path per
|
|
81
|
-
survivor.
|
|
82
|
-
7. **Rank by impact/effort/confidence** using
|
|
83
|
-
\`(impact points / effort cost) * confidence multiplier\` and recommend
|
|
84
|
-
the top survivor.
|
|
85
|
-
8. **Write the artifact** at
|
|
86
|
-
\`${IDEATE_ARTIFACT_PATTERN}\` using the schema in the skill.
|
|
87
|
-
8.5 **Seed shelf (optional).** For critiqued-out or deferred ideas that still
|
|
88
|
-
show upside, write seed notes to
|
|
89
|
-
\`${RUNTIME_ROOT}/seeds/SEED-<YYYY-MM-DD>-<slug>.md\` with
|
|
90
|
-
\`trigger_when\`, hypothesis, and suggested action.
|
|
91
|
-
9. **Present the handoff prompt** with four concrete options — not A/B/C
|
|
92
|
-
letters. Default = "Start /cc on the top recommendation".
|
|
93
|
-
|
|
94
|
-
## Headless mode
|
|
95
|
-
|
|
96
|
-
For skill-to-skill invocation, emit exactly one JSON envelope:
|
|
97
|
-
|
|
98
|
-
\`\`\`json
|
|
99
|
-
{"version":"1","kind":"stage-output","stage":"non-flow","payload":{"command":"/cc-ideate","artifact":".cclaw/artifacts/ideate-<date>-<slug>.md","recommendation":"I-1"},"emittedAt":"<ISO-8601>"}
|
|
100
|
-
\`\`\`
|
|
101
|
-
|
|
102
|
-
Validate envelopes with:
|
|
103
|
-
\`cclaw internal envelope-validate --stdin\`
|
|
104
|
-
|
|
105
|
-
## Primary skill
|
|
106
|
-
|
|
107
|
-
**${RUNTIME_ROOT}/skills/${IDEATE_SKILL_FOLDER}/SKILL.md**
|
|
108
|
-
`;
|
|
109
|
-
}
|
|
110
|
-
export function ideateCommandSkillMarkdown(options = {}) {
|
|
111
|
-
const frames = resolveIdeateFrames(options.frameIds);
|
|
112
|
-
const frameBullets = renderFrameBullets(options.frameIds);
|
|
113
|
-
const minimumDistinctFrames = minimumDistinctIdeateFrames(frames.length, options.mode);
|
|
114
|
-
const frameNames = renderFrameNames(options.frameIds);
|
|
115
|
-
return `---
|
|
116
|
-
name: ${IDEATE_SKILL_NAME}
|
|
117
|
-
description: "Repository ideate mode: detect and rank high-leverage improvements, persist a backlog artifact, and hand off to /cc or save/discard."
|
|
118
|
-
---
|
|
119
|
-
|
|
120
|
-
# /cc-ideate
|
|
121
|
-
|
|
122
|
-
## Announce at start
|
|
123
|
-
|
|
124
|
-
"Using flow-ideate to identify highest-leverage improvements in this
|
|
125
|
-
repository. Will persist a ranked backlog to
|
|
126
|
-
\`${IDEATE_ARTIFACT_PATTERN}\` and end with an explicit handoff."
|
|
127
|
-
|
|
128
|
-
## HARD-GATE
|
|
129
|
-
|
|
130
|
-
${conversationLanguagePolicyMarkdown()}
|
|
131
|
-
- Do not start coding in ideate mode.
|
|
132
|
-
- Do not mutate \`.cclaw/state/flow-state.json\` — ideate mode sits outside
|
|
133
|
-
the critical-path flow.
|
|
134
|
-
- Always produce the artifact file on disk before presenting the handoff.
|
|
135
|
-
- Always end with a structured handoff that names the concrete follow-up
|
|
136
|
-
command for each option. No A/B/C letters without command context.
|
|
137
|
-
|
|
138
|
-
## Protocol
|
|
139
|
-
|
|
140
|
-
### Phase 0 — Resume and classify
|
|
141
|
-
|
|
142
|
-
1. Use the harness's file-glob tool (\`Glob\` pattern
|
|
143
|
-
\`${IDEATE_ARTIFACT_GLOB}\` or equivalent \`ls\`/\`find\`).
|
|
144
|
-
2. Filter to files modified within the last ${IDEATE_RESUME_WINDOW_DAYS} days.
|
|
145
|
-
3. If one or more match, present **one** structured ask using the
|
|
146
|
-
harness's native tool (${STRUCTURED_ASK_TOOLS}) with options:
|
|
147
|
-
- **Continue the existing backlog** — read the most-recent
|
|
148
|
-
ideate-*.md and work from its candidate list; skip re-scanning.
|
|
149
|
-
- **Start a fresh scan** — proceed to Phase 1; the old artifact stays
|
|
150
|
-
on disk for history.
|
|
151
|
-
- **Cancel** — stop; do not scan or write anything.
|
|
152
|
-
4. If no recent artifact exists, proceed to Phase 1 silently.
|
|
153
|
-
5. Classify the ideation mode before grounding:
|
|
154
|
-
- \`repo-grounded\` — explicitly tied to this repository.
|
|
155
|
-
- \`elsewhere-software\` — software problem not tied to this repository.
|
|
156
|
-
- \`elsewhere-non-software\` — process/business/non-software problem.
|
|
157
|
-
- \`narrow\` — a focused prompt where broad frame coverage would be performative.
|
|
158
|
-
6. Record the chosen mode in the artifact.
|
|
159
|
-
|
|
160
|
-
### Phase 1 — Mode-aware grounding
|
|
161
|
-
|
|
162
|
-
Run grounding in parallel where available:
|
|
163
|
-
|
|
164
|
-
- For \`repo-grounded\`:
|
|
165
|
-
- \`rg -n 'TODO|FIXME|XXX|HACK|TBD'\` grouped by file.
|
|
166
|
-
- Test-runner output (\`npm test\`, \`pytest\`, \`go test ./...\`) — note
|
|
167
|
-
failures, timeouts, deprecation warnings.
|
|
168
|
-
- Module size outliers (\`wc -l\` or \`du\`) with weak direct test coverage.
|
|
169
|
-
- Docs drift: check that \`README.md\` / \`docs/\` reference files that still
|
|
170
|
-
exist and flags/APIs that still match \`src/\`.
|
|
171
|
-
- \`${RUNTIME_ROOT}/knowledge.jsonl\` entries with recurring \`type\` in \`rule | pattern | lesson | compound\` and repeated \`trigger/action\` pairs; prefer clusters that already show stable \`origin_run\` history.
|
|
172
|
-
- For \`elsewhere-software\`:
|
|
173
|
-
- Gather current framework/library docs first.
|
|
174
|
-
- Add one comparison scan for established solutions.
|
|
175
|
-
- For \`elsewhere-non-software\`:
|
|
176
|
-
- Capture objective, constraints, and measured friction before proposing fixes.
|
|
177
|
-
|
|
178
|
-
Record each finding with exact evidence (path, command, or doc source).
|
|
179
|
-
|
|
180
|
-
### Phase 2 — Divergent ideation
|
|
181
|
-
|
|
182
|
-
Generate candidate ideas by frame, in parallel when possible:
|
|
183
|
-
|
|
184
|
-
${frameBullets}
|
|
185
|
-
|
|
186
|
-
Require at least ${minimumDistinctFrames} distinct frames in this rendered mode. The
|
|
187
|
-
runtime rule is deterministic: repo-grounded scans require 4 distinct frames;
|
|
188
|
-
narrow, elsewhere-software, and elsewhere-non-software runs require 2; all modes
|
|
189
|
-
are capped by the configured frame count. Avoid frame-collapse (same idea
|
|
190
|
-
rewritten many times). Keep raw outputs for auditability.
|
|
191
|
-
|
|
192
|
-
### Phase 3 — Critique all, keep survivors
|
|
193
|
-
|
|
194
|
-
For each raw candidate:
|
|
195
|
-
|
|
196
|
-
- Write strongest argument **against** this idea.
|
|
197
|
-
- Identify disqualifiers (duplicate, weak evidence, poor ROI, wrong timing).
|
|
198
|
-
- Mark as \`survivor\` or \`critiqued-out\`.
|
|
199
|
-
|
|
200
|
-
Only survivors advance to ranking.
|
|
201
|
-
|
|
202
|
-
### Phase 4 — Rank and write the artifact
|
|
203
|
-
|
|
204
|
-
1. Keep 5–10 survivors.
|
|
205
|
-
2. For each survivor, include:
|
|
206
|
-
- **ID** — \`I-1\`, \`I-2\`, …
|
|
207
|
-
- **Title** — one short imperative phrase
|
|
208
|
-
- **Impact** — High / Medium / Low
|
|
209
|
-
- **Effort** — S / M / L
|
|
210
|
-
- **Confidence** — High / Medium / Low
|
|
211
|
-
- **Evidence** — path(s) or command output, inline if short
|
|
212
|
-
- **Why now** — timing signal from repo evidence, user friction, repeated knowledge, or blocked flow
|
|
213
|
-
- **Expected impact** — concrete user-facing benefit if this lands
|
|
214
|
-
- **Risk** — main implementation/product risk to manage
|
|
215
|
-
- **Counter-argument** — strongest concern that survived
|
|
216
|
-
- **Next /cc prompt** — exact \`/cc <phrase>\` that starts the work
|
|
217
|
-
3. Sort by score \`(impact points / effort cost) * confidence multiplier\`
|
|
218
|
-
and break ties with rationale strength.
|
|
219
|
-
4. Compute the artifact filename:
|
|
220
|
-
- \`slug\` = first 3–5 words of the top recommendation, lowercase,
|
|
221
|
-
non-alphanumeric collapsed to \`-\`, trimmed. When ideate mode is
|
|
222
|
-
focus-hinted (user passed an argument), use the focus hint instead.
|
|
223
|
-
- \`date\` = today in \`YYYY-MM-DD\` (local time).
|
|
224
|
-
- Path = \`.cclaw/artifacts/ideate-<date>-<slug>.md\`.
|
|
225
|
-
5. Use the harness's write-file tool (\`Write\`, \`apply_patch\`, or shell
|
|
226
|
-
\`cat <<EOF > path\`) to create the artifact with this schema:
|
|
227
|
-
|
|
228
|
-
\`\`\`markdown
|
|
229
|
-
# Ideation — <date>
|
|
230
|
-
|
|
231
|
-
**Focus:** <user-supplied focus or "open-ended scan">
|
|
232
|
-
**Mode:** <repo-grounded | elsewhere-software | elsewhere-non-software | narrow>
|
|
233
|
-
**Generated:** <ISO-8601 timestamp>
|
|
234
|
-
**Frames used:** <comma-separated list>
|
|
235
|
-
**Raw candidates:** <N>
|
|
236
|
-
**Critiqued out:** <M>
|
|
237
|
-
**Recommendation:** I-1
|
|
238
|
-
|
|
239
|
-
## Grounding evidence
|
|
240
|
-
|
|
241
|
-
- <signal and evidence>
|
|
242
|
-
- ...
|
|
243
|
-
|
|
244
|
-
## Critiqued out
|
|
245
|
-
|
|
246
|
-
| Idea | Why it was rejected |
|
|
247
|
-
|---|---|
|
|
248
|
-
| ... | ... |
|
|
249
|
-
|
|
250
|
-
## Ranked survivors
|
|
251
|
-
|
|
252
|
-
| ID | Improvement | Why now | Expected impact | Risk | Impact | Effort | Confidence | Evidence | Next /cc prompt |
|
|
253
|
-
|---|---|---|---|---|---|---|---|---|---|
|
|
254
|
-
| I-1 | Simplify a confusing generated prompt surface | Repeated blocker in generated UX | Faster operator recovery | Might over-trim context | High | S | High | <path-to-generated-surface> | \`/cc Simplify the confusing generated prompt surface while preserving behavior\` |
|
|
255
|
-
| … | … | … | … | … | … |
|
|
256
|
-
|
|
257
|
-
## Candidate detail
|
|
258
|
-
|
|
259
|
-
### I-1 — Simplify a confusing generated prompt surface
|
|
260
|
-
- **Evidence:** \`<path>\` contains repeated or stale guidance that a user would see.
|
|
261
|
-
- **Why now:** The prompt is on the daily /cc path, so confusion compounds quickly.
|
|
262
|
-
- **Expected impact:** Operators get a clearer next action without changing gates.
|
|
263
|
-
- **Risk:** Trimming too hard can remove useful orientation for new users.
|
|
264
|
-
- **Next /cc prompt:** \`/cc Simplify the confusing generated prompt surface while preserving behavior\`
|
|
265
|
-
|
|
266
|
-
### I-2 — …
|
|
267
|
-
\`\`\`
|
|
268
|
-
|
|
269
|
-
6. Optional: for promising non-selected ideas, write
|
|
270
|
-
\`${RUNTIME_ROOT}/seeds/SEED-<YYYY-MM-DD>-<slug>.md\` entries with:
|
|
271
|
-
\`title\`, \`trigger_when\`, \`hypothesis\`, \`action\`, and
|
|
272
|
-
\`source_artifact\` = ideate artifact path.
|
|
273
|
-
7. Confirm in chat: "Wrote <path>."
|
|
274
|
-
|
|
275
|
-
### Phase 5 — Handoff prompt
|
|
276
|
-
|
|
277
|
-
Present **one** structured ask using the harness's native tool
|
|
278
|
-
(${STRUCTURED_ASK_TOOLS}). Each option must name the concrete follow-up —
|
|
279
|
-
no bare A/B/C.
|
|
280
|
-
|
|
281
|
-
Required options, in this order:
|
|
282
|
-
|
|
283
|
-
1. **Start /cc on the top recommendation** — the agent immediately loads
|
|
284
|
-
\`${RUNTIME_ROOT}/skills/using-cclaw/SKILL.md\` and invokes
|
|
285
|
-
\`/cc <I-1 handoff phrase>\` in the same turn. Default choice.
|
|
286
|
-
2. **Pick a different candidate** — the agent asks which ID (I-2, I-3, …)
|
|
287
|
-
and then invokes \`/cc <that candidate's handoff phrase>\`.
|
|
288
|
-
3. **Save and close** — leave the artifact on disk, do nothing else.
|
|
289
|
-
Next session: \`/cc-ideate\` will offer to resume it.
|
|
290
|
-
4. **Discard** — delete the just-written artifact. Use only when the
|
|
291
|
-
scan produced nothing actionable.
|
|
292
|
-
|
|
293
|
-
When the structured-ask tool is unavailable, fall back to a plain-text
|
|
294
|
-
lettered list with the same four labels. Do not invent extra options.
|
|
295
|
-
|
|
296
|
-
### Phase 6 — Execute the choice
|
|
297
|
-
|
|
298
|
-
- **Start /cc on I-1** or **different candidate:** announce
|
|
299
|
-
"Handing off to /cc <phrase>" and load the \`using-cclaw\` router
|
|
300
|
-
skill. From there, the normal \`/cc\` classification and stage flow
|
|
301
|
-
takes over. Do not produce a second artifact; the ideate file is
|
|
302
|
-
preserved as the origin document for this run.
|
|
303
|
-
- **Save and close:** reply with the artifact path and stop.
|
|
304
|
-
- **Discard:** delete the artifact file, confirm deletion, stop.
|
|
305
|
-
|
|
306
|
-
## Do not
|
|
307
|
-
|
|
308
|
-
- Do not write into \`.cclaw/artifacts/0X-*.md\` (stage artifacts).
|
|
309
|
-
- Do not mutate \`.cclaw/state/flow-state.json\` at any phase.
|
|
310
|
-
- Do not end the turn with an ungrounded "pick one" question — every
|
|
311
|
-
option in the handoff prompt must reference a concrete command.
|
|
312
|
-
- Do not collapse all ideas into one frame; distribute across:
|
|
313
|
-
${frameNames}.
|
|
314
|
-
`;
|
|
315
|
-
}
|
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
export type IdeateFrameId = "pain-friction" | "inversion" | "assumption-break" | "leverage" | "cross-domain-analogy" | "constraint-flip";
|
|
2
|
-
export interface IdeateFrame {
|
|
3
|
-
id: IdeateFrameId;
|
|
4
|
-
label: string;
|
|
5
|
-
prompt: string;
|
|
6
|
-
examplePatterns: string[];
|
|
7
|
-
}
|
|
8
|
-
export interface IdeateFrameDispatchInput {
|
|
9
|
-
focus: string;
|
|
10
|
-
mode: "repo-grounded" | "elsewhere-software" | "elsewhere-non-software";
|
|
11
|
-
signalSummary: string[];
|
|
12
|
-
}
|
|
13
|
-
export interface IdeateFrameDispatchPlanEntry {
|
|
14
|
-
frameId: IdeateFrameId;
|
|
15
|
-
label: string;
|
|
16
|
-
prompt: string;
|
|
17
|
-
}
|
|
18
|
-
export interface IdeateCandidateDraft {
|
|
19
|
-
title: string;
|
|
20
|
-
evidencePath: string;
|
|
21
|
-
summary: string;
|
|
22
|
-
frameId: IdeateFrameId;
|
|
23
|
-
}
|
|
24
|
-
export interface IdeateCandidateMerged extends Omit<IdeateCandidateDraft, "frameId"> {
|
|
25
|
-
frameIds: IdeateFrameId[];
|
|
26
|
-
}
|
|
27
|
-
export declare const DEFAULT_IDEATE_FRAME_IDS: readonly IdeateFrameId[];
|
|
28
|
-
export declare const IDEATE_FRAMES: readonly IdeateFrame[];
|
|
29
|
-
export declare function resolveIdeateFrames(frameIds?: readonly IdeateFrameId[]): IdeateFrame[];
|
|
30
|
-
export declare function buildIdeateFrameDispatchPlan(input: IdeateFrameDispatchInput, frameIds?: readonly IdeateFrameId[]): IdeateFrameDispatchPlanEntry[];
|
|
31
|
-
export declare function dedupeIdeateCandidates(drafts: readonly IdeateCandidateDraft[]): IdeateCandidateMerged[];
|
|
@@ -1,140 +0,0 @@
|
|
|
1
|
-
const FRAME_REGISTRY = {
|
|
2
|
-
"pain-friction": {
|
|
3
|
-
id: "pain-friction",
|
|
4
|
-
label: "pain/friction",
|
|
5
|
-
prompt: "Find repeated friction in the repo workflow. Prioritize changes that eliminate recurring toil, fragile handoffs, or repeated manual recovery.",
|
|
6
|
-
examplePatterns: [
|
|
7
|
-
"Repeated TODO/FIXME hotspots in one subsystem",
|
|
8
|
-
"Flows that require manual retries or ad-hoc scripts",
|
|
9
|
-
"Developer loops slowed by avoidable boilerplate"
|
|
10
|
-
]
|
|
11
|
-
},
|
|
12
|
-
inversion: {
|
|
13
|
-
id: "inversion",
|
|
14
|
-
label: "inversion",
|
|
15
|
-
prompt: "Invert a dominant assumption in the current implementation (e.g., push vs pull, synchronous vs queued, implicit vs explicit) and evaluate upside.",
|
|
16
|
-
examplePatterns: [
|
|
17
|
-
"Replace optimistic assumptions with fail-closed defaults",
|
|
18
|
-
"Switch from post-facto checks to pre-flight validation",
|
|
19
|
-
"Move from global policy to module-local contracts"
|
|
20
|
-
]
|
|
21
|
-
},
|
|
22
|
-
"assumption-break": {
|
|
23
|
-
id: "assumption-break",
|
|
24
|
-
label: "assumption-break",
|
|
25
|
-
prompt: "List assumptions that might be false in production. Generate ideas that remain correct even when those assumptions fail.",
|
|
26
|
-
examplePatterns: [
|
|
27
|
-
"Edge paths currently treated as impossible",
|
|
28
|
-
"Implicit coupling between modules with no explicit contract",
|
|
29
|
-
"Latency, scale, or environment assumptions baked into logic"
|
|
30
|
-
]
|
|
31
|
-
},
|
|
32
|
-
leverage: {
|
|
33
|
-
id: "leverage",
|
|
34
|
-
label: "leverage",
|
|
35
|
-
prompt: "Target interventions with asymmetric payoff: one change that improves multiple stages, teams, or failure classes at once.",
|
|
36
|
-
examplePatterns: [
|
|
37
|
-
"A shared helper replacing duplicated logic in many files",
|
|
38
|
-
"One lint/gate that blocks an entire class of regressions",
|
|
39
|
-
"A protocol update that improves multiple stage outputs"
|
|
40
|
-
]
|
|
41
|
-
},
|
|
42
|
-
"cross-domain-analogy": {
|
|
43
|
-
id: "cross-domain-analogy",
|
|
44
|
-
label: "cross-domain analogy",
|
|
45
|
-
prompt: "Borrow a proven pattern from another domain and adapt it to this repo. Keep it concrete and grounded in local constraints.",
|
|
46
|
-
examplePatterns: [
|
|
47
|
-
"Apply SRE-style error budgets to planning artifacts",
|
|
48
|
-
"Use security threat-model thinking for reliability design",
|
|
49
|
-
"Import CI release-train discipline into stage completion gates"
|
|
50
|
-
]
|
|
51
|
-
},
|
|
52
|
-
"constraint-flip": {
|
|
53
|
-
id: "constraint-flip",
|
|
54
|
-
label: "constraint-flip",
|
|
55
|
-
prompt: "Flip one assumed constraint (time, team size, risk tolerance, compatibility) and derive better options under the new boundary.",
|
|
56
|
-
examplePatterns: [
|
|
57
|
-
"Assume near-zero migration window and redesign rollout",
|
|
58
|
-
"Assume one maintainer and optimize for low operational burden",
|
|
59
|
-
"Assume strict auditability and remove ambiguous behaviors"
|
|
60
|
-
]
|
|
61
|
-
}
|
|
62
|
-
};
|
|
63
|
-
export const DEFAULT_IDEATE_FRAME_IDS = Object.freeze([
|
|
64
|
-
"pain-friction",
|
|
65
|
-
"inversion",
|
|
66
|
-
"assumption-break",
|
|
67
|
-
"leverage",
|
|
68
|
-
"cross-domain-analogy",
|
|
69
|
-
"constraint-flip"
|
|
70
|
-
]);
|
|
71
|
-
export const IDEATE_FRAMES = Object.freeze(DEFAULT_IDEATE_FRAME_IDS.map((id) => FRAME_REGISTRY[id]));
|
|
72
|
-
export function resolveIdeateFrames(frameIds) {
|
|
73
|
-
if (!frameIds || frameIds.length === 0) {
|
|
74
|
-
return [...IDEATE_FRAMES];
|
|
75
|
-
}
|
|
76
|
-
const seen = new Set();
|
|
77
|
-
const resolved = [];
|
|
78
|
-
for (const rawId of frameIds) {
|
|
79
|
-
if (!DEFAULT_IDEATE_FRAME_IDS.includes(rawId)) {
|
|
80
|
-
throw new Error(`Unknown ideate frame id: ${rawId}`);
|
|
81
|
-
}
|
|
82
|
-
if (seen.has(rawId))
|
|
83
|
-
continue;
|
|
84
|
-
seen.add(rawId);
|
|
85
|
-
resolved.push(FRAME_REGISTRY[rawId]);
|
|
86
|
-
}
|
|
87
|
-
return resolved;
|
|
88
|
-
}
|
|
89
|
-
export function buildIdeateFrameDispatchPlan(input, frameIds) {
|
|
90
|
-
const signalBlock = input.signalSummary.length > 0
|
|
91
|
-
? input.signalSummary.map((line) => `- ${line}`).join("\n")
|
|
92
|
-
: "- no pre-scan signals captured yet";
|
|
93
|
-
return resolveIdeateFrames(frameIds).map((frame) => ({
|
|
94
|
-
frameId: frame.id,
|
|
95
|
-
label: frame.label,
|
|
96
|
-
prompt: [
|
|
97
|
-
`Frame: ${frame.label} (${frame.id})`,
|
|
98
|
-
`Mode: ${input.mode}`,
|
|
99
|
-
`Focus: ${input.focus || "open-ended scan"}`,
|
|
100
|
-
"",
|
|
101
|
-
"Signal summary:",
|
|
102
|
-
signalBlock,
|
|
103
|
-
"",
|
|
104
|
-
`Frame prompt: ${frame.prompt}`,
|
|
105
|
-
"",
|
|
106
|
-
"Generate 3-5 concrete candidates with repo-grounded evidence."
|
|
107
|
-
].join("\n")
|
|
108
|
-
}));
|
|
109
|
-
}
|
|
110
|
-
function normalizeCandidateKey(title, evidencePath) {
|
|
111
|
-
const normalizedTitle = title.trim().toLowerCase().replace(/[^a-z0-9]+/gu, " ").trim();
|
|
112
|
-
const normalizedEvidence = evidencePath
|
|
113
|
-
.trim()
|
|
114
|
-
.toLowerCase()
|
|
115
|
-
.replace(/\\/gu, "/");
|
|
116
|
-
return `${normalizedTitle}::${normalizedEvidence}`;
|
|
117
|
-
}
|
|
118
|
-
export function dedupeIdeateCandidates(drafts) {
|
|
119
|
-
const merged = new Map();
|
|
120
|
-
for (const draft of drafts) {
|
|
121
|
-
const key = normalizeCandidateKey(draft.title, draft.evidencePath);
|
|
122
|
-
const existing = merged.get(key);
|
|
123
|
-
if (!existing) {
|
|
124
|
-
merged.set(key, {
|
|
125
|
-
title: draft.title,
|
|
126
|
-
evidencePath: draft.evidencePath,
|
|
127
|
-
summary: draft.summary,
|
|
128
|
-
frameIds: [draft.frameId]
|
|
129
|
-
});
|
|
130
|
-
continue;
|
|
131
|
-
}
|
|
132
|
-
if (!existing.frameIds.includes(draft.frameId)) {
|
|
133
|
-
existing.frameIds.push(draft.frameId);
|
|
134
|
-
}
|
|
135
|
-
if (draft.summary.length > existing.summary.length) {
|
|
136
|
-
existing.summary = draft.summary;
|
|
137
|
-
}
|
|
138
|
-
}
|
|
139
|
-
return [...merged.values()];
|
|
140
|
-
}
|
|
@@ -1,25 +0,0 @@
|
|
|
1
|
-
export type IdeateImpact = "high" | "medium" | "low";
|
|
2
|
-
export type IdeateEffort = "s" | "m" | "l";
|
|
3
|
-
export type IdeateConfidence = "high" | "medium" | "low";
|
|
4
|
-
export interface IdeateCandidateEvaluationInput {
|
|
5
|
-
id: string;
|
|
6
|
-
title: string;
|
|
7
|
-
impact: IdeateImpact;
|
|
8
|
-
effort: IdeateEffort;
|
|
9
|
-
confidence: IdeateConfidence;
|
|
10
|
-
rationaleStrength: number;
|
|
11
|
-
counterArgumentStrength: number;
|
|
12
|
-
}
|
|
13
|
-
export interface IdeateCandidateEvaluation extends IdeateCandidateEvaluationInput {
|
|
14
|
-
disposition: "survivor" | "critiqued-out";
|
|
15
|
-
rankingScore: number;
|
|
16
|
-
}
|
|
17
|
-
export interface IdeateRankingResult {
|
|
18
|
-
survivors: IdeateCandidateEvaluation[];
|
|
19
|
-
critiquedOut: IdeateCandidateEvaluation[];
|
|
20
|
-
recommendationId: string | null;
|
|
21
|
-
}
|
|
22
|
-
export declare function isCritiquedOut(rationaleStrength: number, counterArgumentStrength: number): boolean;
|
|
23
|
-
export declare function scoreIdeateCandidate(impact: IdeateImpact, effort: IdeateEffort, confidence: IdeateConfidence): number;
|
|
24
|
-
export declare function evaluateIdeateCandidate(input: IdeateCandidateEvaluationInput): IdeateCandidateEvaluation;
|
|
25
|
-
export declare function rankIdeateCandidates(inputs: readonly IdeateCandidateEvaluationInput[], maxSurvivors?: number): IdeateRankingResult;
|
|
@@ -1,65 +0,0 @@
|
|
|
1
|
-
const IMPACT_POINTS = {
|
|
2
|
-
high: 9,
|
|
3
|
-
medium: 6,
|
|
4
|
-
low: 3
|
|
5
|
-
};
|
|
6
|
-
const EFFORT_COST = {
|
|
7
|
-
s: 1,
|
|
8
|
-
m: 2,
|
|
9
|
-
l: 3
|
|
10
|
-
};
|
|
11
|
-
const CONFIDENCE_MULTIPLIER = {
|
|
12
|
-
high: 1,
|
|
13
|
-
medium: 0.75,
|
|
14
|
-
low: 0.5
|
|
15
|
-
};
|
|
16
|
-
function clampStrength(value) {
|
|
17
|
-
if (!Number.isFinite(value))
|
|
18
|
-
return 0;
|
|
19
|
-
if (value < 0)
|
|
20
|
-
return 0;
|
|
21
|
-
if (value > 1)
|
|
22
|
-
return 1;
|
|
23
|
-
return value;
|
|
24
|
-
}
|
|
25
|
-
export function isCritiquedOut(rationaleStrength, counterArgumentStrength) {
|
|
26
|
-
return clampStrength(counterArgumentStrength) > clampStrength(rationaleStrength);
|
|
27
|
-
}
|
|
28
|
-
export function scoreIdeateCandidate(impact, effort, confidence) {
|
|
29
|
-
const raw = (IMPACT_POINTS[impact] / EFFORT_COST[effort]) * CONFIDENCE_MULTIPLIER[confidence];
|
|
30
|
-
return Number(raw.toFixed(3));
|
|
31
|
-
}
|
|
32
|
-
export function evaluateIdeateCandidate(input) {
|
|
33
|
-
const disposition = isCritiquedOut(input.rationaleStrength, input.counterArgumentStrength)
|
|
34
|
-
? "critiqued-out"
|
|
35
|
-
: "survivor";
|
|
36
|
-
return {
|
|
37
|
-
...input,
|
|
38
|
-
disposition,
|
|
39
|
-
rankingScore: scoreIdeateCandidate(input.impact, input.effort, input.confidence)
|
|
40
|
-
};
|
|
41
|
-
}
|
|
42
|
-
export function rankIdeateCandidates(inputs, maxSurvivors = 10) {
|
|
43
|
-
const evaluated = inputs.map(evaluateIdeateCandidate);
|
|
44
|
-
const survivors = evaluated
|
|
45
|
-
.filter((candidate) => candidate.disposition === "survivor")
|
|
46
|
-
.sort((left, right) => {
|
|
47
|
-
if (right.rankingScore !== left.rankingScore) {
|
|
48
|
-
return right.rankingScore - left.rankingScore;
|
|
49
|
-
}
|
|
50
|
-
if (right.rationaleStrength !== left.rationaleStrength) {
|
|
51
|
-
return right.rationaleStrength - left.rationaleStrength;
|
|
52
|
-
}
|
|
53
|
-
return left.id.localeCompare(right.id);
|
|
54
|
-
})
|
|
55
|
-
.slice(0, Math.max(0, maxSurvivors));
|
|
56
|
-
const survivorIds = new Set(survivors.map((candidate) => candidate.id));
|
|
57
|
-
const critiquedOut = evaluated
|
|
58
|
-
.filter((candidate) => candidate.disposition === "critiqued-out" || !survivorIds.has(candidate.id))
|
|
59
|
-
.sort((left, right) => left.id.localeCompare(right.id));
|
|
60
|
-
return {
|
|
61
|
-
survivors,
|
|
62
|
-
critiquedOut,
|
|
63
|
-
recommendationId: survivors[0]?.id ?? null
|
|
64
|
-
};
|
|
65
|
-
}
|
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Single source of truth for how /cc-next should treat Ralph Loop status.
|
|
3
|
-
*
|
|
4
|
-
* IMPORTANT: Ralph Loop is a **progress indicator + soft pre-advance nudge**,
|
|
5
|
-
* not a hard gate. Hard enforcement always flows through flow-state.json
|
|
6
|
-
* gates via `stage-complete.mjs`. Both the command contract and the skill
|
|
7
|
-
* document render this same paragraph to prevent drift — see
|
|
8
|
-
* `tests/e2e/next-command-ralph-loop-contract.test.ts`.
|
|
9
|
-
*/
|
|
10
|
-
export declare const RALPH_LOOP_CONTRACT_MARKER = "ralph-loop-contract:v1";
|
|
11
|
-
export declare function ralphLoopContractSnippet(): string;
|
|
12
|
-
/**
|
|
13
|
-
* Internal compatibility contract for /cc-next.
|
|
14
|
-
* /cc is the promoted public progression command; this remains as an internal/legacy alias.
|
|
15
|
-
*/
|
|
16
|
-
export declare function nextCommandContract(): string;
|
|
17
|
-
/**
|
|
18
|
-
* Skill body for /cc-next — the primary flow progression command.
|
|
19
|
-
*/
|
|
20
|
-
export declare function nextCommandSkillMarkdown(): string;
|