cclaw-cli 0.30.0 → 0.32.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 +45 -24
- package/dist/cli.d.ts +2 -4
- package/dist/cli.js +48 -133
- package/dist/config.d.ts +1 -11
- package/dist/config.js +0 -40
- package/dist/content/archive-command.js +58 -32
- package/dist/content/compound-command.js +79 -24
- package/dist/content/next-command.js +40 -8
- package/dist/content/protocols.js +39 -8
- package/dist/content/retro-command.js +104 -32
- package/dist/doctor.js +0 -2
- package/dist/flow-state.d.ts +31 -0
- package/dist/flow-state.js +37 -1
- package/dist/harness-adapters.js +19 -7
- package/dist/install.d.ts +3 -5
- package/dist/install.js +4 -9
- package/dist/runs.js +39 -4
- package/dist/types.d.ts +0 -12
- package/dist/types.js +0 -11
- package/package.json +1 -1
package/dist/install.js
CHANGED
|
@@ -3,7 +3,7 @@ import fs from "node:fs/promises";
|
|
|
3
3
|
import path from "node:path";
|
|
4
4
|
import { promisify } from "node:util";
|
|
5
5
|
import { CCLAW_VERSION, COMMAND_FILE_ORDER, FLOW_VERSION, REQUIRED_DIRS, RUNTIME_ROOT } from "./constants.js";
|
|
6
|
-
import { writeConfig, createDefaultConfig,
|
|
6
|
+
import { writeConfig, createDefaultConfig, readConfig, configPath } from "./config.js";
|
|
7
7
|
import { commandContract } from "./content/contracts.js";
|
|
8
8
|
import { contextModeFiles, createInitialContextModeState } from "./content/contexts.js";
|
|
9
9
|
import { learnSkillMarkdown, learnCommandContract } from "./content/learnings.js";
|
|
@@ -1088,12 +1088,7 @@ async function materializeRuntime(projectRoot, config, forceStateReset) {
|
|
|
1088
1088
|
await ensureGitignore(projectRoot);
|
|
1089
1089
|
}
|
|
1090
1090
|
export async function initCclaw(options) {
|
|
1091
|
-
const config = options.
|
|
1092
|
-
? createProfileConfig(options.profile, {
|
|
1093
|
-
harnesses: options.harnesses,
|
|
1094
|
-
defaultTrack: options.track
|
|
1095
|
-
})
|
|
1096
|
-
: createDefaultConfig(options.harnesses, options.track);
|
|
1091
|
+
const config = createDefaultConfig(options.harnesses, options.track);
|
|
1097
1092
|
await writeConfig(options.projectRoot, config);
|
|
1098
1093
|
await materializeRuntime(options.projectRoot, config, true);
|
|
1099
1094
|
}
|
|
@@ -1111,8 +1106,8 @@ export async function syncCclaw(projectRoot) {
|
|
|
1111
1106
|
* `promptGuardMode`, `tddEnforcement`, `gitHookGuards`, `languageRulePacks`,
|
|
1112
1107
|
* and `trackHeuristics` are preserved verbatim from the existing config.
|
|
1113
1108
|
*
|
|
1114
|
-
* For an explicit reset
|
|
1115
|
-
*
|
|
1109
|
+
* For an explicit reset, run `cclaw-cli uninstall && cclaw-cli init`
|
|
1110
|
+
* (after optionally archiving the current run via `/cc-ops archive`).
|
|
1116
1111
|
*/
|
|
1117
1112
|
export async function upgradeCclaw(projectRoot) {
|
|
1118
1113
|
const existing = await readConfig(projectRoot);
|
package/dist/runs.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import fs from "node:fs/promises";
|
|
2
2
|
import path from "node:path";
|
|
3
3
|
import { COMMAND_FILE_ORDER, RUNTIME_ROOT } from "./constants.js";
|
|
4
|
-
import { canTransition, createInitialFlowState, isFlowTrack, skippedStagesForTrack } from "./flow-state.js";
|
|
4
|
+
import { canTransition, createInitialCloseoutState, createInitialFlowState, isFlowTrack, skippedStagesForTrack, SHIP_SUBSTATES } from "./flow-state.js";
|
|
5
5
|
import { ensureFeatureSystem, readActiveFeature, syncActiveFeatureSnapshot } from "./feature-system.js";
|
|
6
6
|
import { ensureDir, exists, withDirectoryLock, writeFileSafe } from "./fs-utils.js";
|
|
7
7
|
export class InvalidStageTransitionError extends Error {
|
|
@@ -272,6 +272,37 @@ function sanitizeRetroState(value) {
|
|
|
272
272
|
compoundEntries
|
|
273
273
|
};
|
|
274
274
|
}
|
|
275
|
+
function isShipSubstate(value) {
|
|
276
|
+
return typeof value === "string" && SHIP_SUBSTATES.includes(value);
|
|
277
|
+
}
|
|
278
|
+
function sanitizeCloseoutState(value) {
|
|
279
|
+
const fallback = createInitialCloseoutState();
|
|
280
|
+
if (!value || typeof value !== "object" || Array.isArray(value)) {
|
|
281
|
+
return fallback;
|
|
282
|
+
}
|
|
283
|
+
const typed = value;
|
|
284
|
+
const shipSubstate = isShipSubstate(typed.shipSubstate) ? typed.shipSubstate : fallback.shipSubstate;
|
|
285
|
+
const retroDraftedAt = typeof typed.retroDraftedAt === "string" ? typed.retroDraftedAt : undefined;
|
|
286
|
+
const retroAcceptedAt = typeof typed.retroAcceptedAt === "string" ? typed.retroAcceptedAt : undefined;
|
|
287
|
+
const retroSkipped = typeof typed.retroSkipped === "boolean" ? typed.retroSkipped : undefined;
|
|
288
|
+
const retroSkipReason = typeof typed.retroSkipReason === "string" ? typed.retroSkipReason : undefined;
|
|
289
|
+
const compoundCompletedAt = typeof typed.compoundCompletedAt === "string" ? typed.compoundCompletedAt : undefined;
|
|
290
|
+
const compoundSkipped = typeof typed.compoundSkipped === "boolean" ? typed.compoundSkipped : undefined;
|
|
291
|
+
const promotedRaw = typed.compoundPromoted;
|
|
292
|
+
const compoundPromoted = typeof promotedRaw === "number" && Number.isFinite(promotedRaw) && promotedRaw >= 0
|
|
293
|
+
? Math.floor(promotedRaw)
|
|
294
|
+
: 0;
|
|
295
|
+
return {
|
|
296
|
+
shipSubstate,
|
|
297
|
+
retroDraftedAt,
|
|
298
|
+
retroAcceptedAt,
|
|
299
|
+
retroSkipped,
|
|
300
|
+
retroSkipReason,
|
|
301
|
+
compoundCompletedAt,
|
|
302
|
+
compoundSkipped,
|
|
303
|
+
compoundPromoted
|
|
304
|
+
};
|
|
305
|
+
}
|
|
275
306
|
function coerceFlowState(parsed) {
|
|
276
307
|
const track = coerceTrack(parsed.track);
|
|
277
308
|
const next = createInitialFlowState("active", track);
|
|
@@ -289,7 +320,8 @@ function coerceFlowState(parsed) {
|
|
|
289
320
|
skippedStages: sanitizeSkippedStages(parsed.skippedStages, track),
|
|
290
321
|
staleStages: sanitizeStaleStages(parsed.staleStages),
|
|
291
322
|
rewinds: sanitizeRewinds(parsed.rewinds),
|
|
292
|
-
retro: sanitizeRetroState(parsed.retro)
|
|
323
|
+
retro: sanitizeRetroState(parsed.retro),
|
|
324
|
+
closeout: sanitizeCloseoutState(parsed.closeout)
|
|
293
325
|
};
|
|
294
326
|
}
|
|
295
327
|
function toArchiveDate(date = new Date()) {
|
|
@@ -536,9 +568,12 @@ export async function archiveRun(projectRoot, featureName, options = {}) {
|
|
|
536
568
|
if (skipRetro && (!skipRetroReason || skipRetroReason.length === 0)) {
|
|
537
569
|
throw new Error("archive --skip-retro requires --retro-reason=<text>.");
|
|
538
570
|
}
|
|
539
|
-
|
|
571
|
+
const retroSkippedInCloseout = sourceState.closeout.retroSkipped === true &&
|
|
572
|
+
typeof sourceState.closeout.retroSkipReason === "string" &&
|
|
573
|
+
sourceState.closeout.retroSkipReason.trim().length > 0;
|
|
574
|
+
if (retroGate.required && !retroGate.completed && !skipRetro && !retroSkippedInCloseout) {
|
|
540
575
|
throw new Error("Archive blocked: retro gate is required after ship completion. " +
|
|
541
|
-
"Run /cc-
|
|
576
|
+
"Run /cc-next (auto-runs retro) or, for CLI-only flows, re-run `cclaw archive --skip-retro --retro-reason=<text>`.");
|
|
542
577
|
}
|
|
543
578
|
if (retroGate.completed) {
|
|
544
579
|
const completedAt = sourceState.retro.completedAt ?? new Date().toISOString();
|
package/dist/types.d.ts
CHANGED
|
@@ -15,18 +15,6 @@ export type FlowTrack = (typeof FLOW_TRACKS)[number];
|
|
|
15
15
|
export declare const TRACK_STAGES: Record<FlowTrack, readonly FlowStage[]>;
|
|
16
16
|
export declare const HARNESS_IDS: readonly ["claude", "cursor", "opencode", "codex"];
|
|
17
17
|
export type HarnessId = (typeof HARNESS_IDS)[number];
|
|
18
|
-
/**
|
|
19
|
-
* Init profiles pre-fill `cclaw init` flags for common install shapes.
|
|
20
|
-
*
|
|
21
|
-
* - `minimal` — single-harness (claude), medium track default, no git hook guards. For solo
|
|
22
|
-
* contributors who still want brainstorm/spec/plan rigor without full scope+design overhead.
|
|
23
|
-
* - `standard` — default harness set, standard track, no git hook guards, advisory guards.
|
|
24
|
-
* Matches the pre-profile default behavior.
|
|
25
|
-
* - `full` — default harness set, standard track, git hook guards on, strict prompt guards.
|
|
26
|
-
* For teams that want every safety rail on.
|
|
27
|
-
*/
|
|
28
|
-
export declare const INIT_PROFILES: readonly ["minimal", "standard", "full"];
|
|
29
|
-
export type InitProfile = (typeof INIT_PROFILES)[number];
|
|
30
18
|
/**
|
|
31
19
|
* Opt-in language rule packs. When enabled in config, `cclaw sync` installs the
|
|
32
20
|
* corresponding utility skill so the meta-skill router can load language-specific
|
package/dist/types.js
CHANGED
|
@@ -25,17 +25,6 @@ export const TRACK_STAGES = {
|
|
|
25
25
|
quick: ["spec", "tdd", "review", "ship"]
|
|
26
26
|
};
|
|
27
27
|
export const HARNESS_IDS = ["claude", "cursor", "opencode", "codex"];
|
|
28
|
-
/**
|
|
29
|
-
* Init profiles pre-fill `cclaw init` flags for common install shapes.
|
|
30
|
-
*
|
|
31
|
-
* - `minimal` — single-harness (claude), medium track default, no git hook guards. For solo
|
|
32
|
-
* contributors who still want brainstorm/spec/plan rigor without full scope+design overhead.
|
|
33
|
-
* - `standard` — default harness set, standard track, no git hook guards, advisory guards.
|
|
34
|
-
* Matches the pre-profile default behavior.
|
|
35
|
-
* - `full` — default harness set, standard track, git hook guards on, strict prompt guards.
|
|
36
|
-
* For teams that want every safety rail on.
|
|
37
|
-
*/
|
|
38
|
-
export const INIT_PROFILES = ["minimal", "standard", "full"];
|
|
39
28
|
/**
|
|
40
29
|
* Opt-in language rule packs. When enabled in config, `cclaw sync` installs the
|
|
41
30
|
* corresponding utility skill so the meta-skill router can load language-specific
|