@paths.design/caws-cli 10.2.0 → 11.1.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 +125 -374
- package/dist/index.js +45 -787
- package/dist/init/harness-detect.d.ts +18 -0
- package/dist/init/harness-detect.d.ts.map +1 -0
- package/dist/init/harness-detect.js +90 -0
- package/dist/init/harness-detect.js.map +1 -0
- package/dist/init/hook-install.d.ts +53 -0
- package/dist/init/hook-install.d.ts.map +1 -0
- package/dist/init/hook-install.js +421 -0
- package/dist/init/hook-install.js.map +1 -0
- package/dist/init/hook-packs/manifest-claude-code.d.ts +4 -0
- package/dist/init/hook-packs/manifest-claude-code.d.ts.map +1 -0
- package/dist/init/hook-packs/manifest-claude-code.js +190 -0
- package/dist/init/hook-packs/manifest-claude-code.js.map +1 -0
- package/dist/init/hook-packs/register.d.ts +19 -0
- package/dist/init/hook-packs/register.d.ts.map +1 -0
- package/dist/init/hook-packs/register.js +37 -0
- package/dist/init/hook-packs/register.js.map +1 -0
- package/dist/init/hook-packs/types.d.ts +123 -0
- package/dist/init/hook-packs/types.d.ts.map +1 -0
- package/dist/init/hook-packs/types.js +29 -0
- package/dist/init/hook-packs/types.js.map +1 -0
- package/dist/shell/binding/resolve-binding.d.ts +4 -0
- package/dist/shell/binding/resolve-binding.d.ts.map +1 -0
- package/dist/shell/binding/resolve-binding.js +228 -0
- package/dist/shell/binding/resolve-binding.js.map +1 -0
- package/dist/shell/binding/types.d.ts +42 -0
- package/dist/shell/binding/types.d.ts.map +1 -0
- package/dist/shell/binding/types.js +21 -0
- package/dist/shell/binding/types.js.map +1 -0
- package/dist/shell/commands/claim.d.ts +14 -0
- package/dist/shell/commands/claim.d.ts.map +1 -0
- package/dist/shell/commands/claim.js +197 -0
- package/dist/shell/commands/claim.js.map +1 -0
- package/dist/shell/commands/doctor.d.ts +13 -0
- package/dist/shell/commands/doctor.d.ts.map +1 -0
- package/dist/shell/commands/doctor.js +97 -0
- package/dist/shell/commands/doctor.js.map +1 -0
- package/dist/shell/commands/evidence.d.ts +28 -0
- package/dist/shell/commands/evidence.d.ts.map +1 -0
- package/dist/shell/commands/evidence.js +166 -0
- package/dist/shell/commands/evidence.js.map +1 -0
- package/dist/shell/commands/gates.d.ts +19 -0
- package/dist/shell/commands/gates.d.ts.map +1 -0
- package/dist/shell/commands/gates.js +208 -0
- package/dist/shell/commands/gates.js.map +1 -0
- package/dist/shell/commands/init.d.ts +17 -0
- package/dist/shell/commands/init.d.ts.map +1 -0
- package/dist/shell/commands/init.js +168 -0
- package/dist/shell/commands/init.js.map +1 -0
- package/dist/shell/commands/scope.d.ts +11 -0
- package/dist/shell/commands/scope.d.ts.map +1 -0
- package/dist/shell/commands/scope.js +92 -0
- package/dist/shell/commands/scope.js.map +1 -0
- package/dist/shell/commands/specs.d.ts +41 -0
- package/dist/shell/commands/specs.d.ts.map +1 -0
- package/dist/shell/commands/specs.js +264 -0
- package/dist/shell/commands/specs.js.map +1 -0
- package/dist/shell/commands/status.d.ts +15 -0
- package/dist/shell/commands/status.d.ts.map +1 -0
- package/dist/shell/commands/status.js +106 -0
- package/dist/shell/commands/status.js.map +1 -0
- package/dist/shell/commands/waiver.d.ts +38 -0
- package/dist/shell/commands/waiver.d.ts.map +1 -0
- package/dist/shell/commands/waiver.js +240 -0
- package/dist/shell/commands/waiver.js.map +1 -0
- package/dist/shell/commands/worktree.d.ts +38 -0
- package/dist/shell/commands/worktree.d.ts.map +1 -0
- package/dist/shell/commands/worktree.js +286 -0
- package/dist/shell/commands/worktree.js.map +1 -0
- package/dist/shell/gates/disposition.d.ts +23 -0
- package/dist/shell/gates/disposition.d.ts.map +1 -0
- package/dist/shell/gates/disposition.js +117 -0
- package/dist/shell/gates/disposition.js.map +1 -0
- package/dist/shell/gates/gate-result-contract.d.ts +39 -0
- package/dist/shell/gates/gate-result-contract.d.ts.map +1 -0
- package/dist/shell/gates/gate-result-contract.js +150 -0
- package/dist/shell/gates/gate-result-contract.js.map +1 -0
- package/dist/shell/gates/local-evaluators/budget-limit.d.ts +24 -0
- package/dist/shell/gates/local-evaluators/budget-limit.d.ts.map +1 -0
- package/dist/shell/gates/local-evaluators/budget-limit.js +67 -0
- package/dist/shell/gates/local-evaluators/budget-limit.js.map +1 -0
- package/dist/shell/gates/local-evaluators/diff-helpers.d.ts +25 -0
- package/dist/shell/gates/local-evaluators/diff-helpers.d.ts.map +1 -0
- package/dist/shell/gates/local-evaluators/diff-helpers.js +74 -0
- package/dist/shell/gates/local-evaluators/diff-helpers.js.map +1 -0
- package/dist/shell/gates/local-evaluators/index.d.ts +28 -0
- package/dist/shell/gates/local-evaluators/index.d.ts.map +1 -0
- package/dist/shell/gates/local-evaluators/index.js +67 -0
- package/dist/shell/gates/local-evaluators/index.js.map +1 -0
- package/dist/shell/gates/local-evaluators/scope-boundary.d.ts +23 -0
- package/dist/shell/gates/local-evaluators/scope-boundary.d.ts.map +1 -0
- package/dist/shell/gates/local-evaluators/scope-boundary.js +67 -0
- package/dist/shell/gates/local-evaluators/scope-boundary.js.map +1 -0
- package/dist/shell/gates/local-evaluators/spec-completeness.d.ts +12 -0
- package/dist/shell/gates/local-evaluators/spec-completeness.d.ts.map +1 -0
- package/dist/shell/gates/local-evaluators/spec-completeness.js +73 -0
- package/dist/shell/gates/local-evaluators/spec-completeness.js.map +1 -0
- package/dist/shell/gates/quality-gates-adapter.d.ts +55 -0
- package/dist/shell/gates/quality-gates-adapter.d.ts.map +1 -0
- package/dist/shell/gates/quality-gates-adapter.js +161 -0
- package/dist/shell/gates/quality-gates-adapter.js.map +1 -0
- package/dist/shell/gates/waiver-filter.d.ts +58 -0
- package/dist/shell/gates/waiver-filter.d.ts.map +1 -0
- package/dist/shell/gates/waiver-filter.js +119 -0
- package/dist/shell/gates/waiver-filter.js.map +1 -0
- package/dist/shell/index.d.ts +54 -0
- package/dist/shell/index.d.ts.map +1 -0
- package/dist/shell/index.js +85 -0
- package/dist/shell/index.js.map +1 -0
- package/dist/shell/register.d.ts +11 -0
- package/dist/shell/register.d.ts.map +1 -0
- package/dist/shell/register.js +464 -0
- package/dist/shell/register.js.map +1 -0
- package/dist/shell/render/claim.d.ts +22 -0
- package/dist/shell/render/claim.d.ts.map +1 -0
- package/dist/shell/render/claim.js +75 -0
- package/dist/shell/render/claim.js.map +1 -0
- package/dist/shell/render/decision.d.ts +15 -0
- package/dist/shell/render/decision.d.ts.map +1 -0
- package/dist/shell/render/decision.js +66 -0
- package/dist/shell/render/decision.js.map +1 -0
- package/dist/shell/render/diagnostic.d.ts +19 -0
- package/dist/shell/render/diagnostic.d.ts.map +1 -0
- package/dist/shell/render/diagnostic.js +76 -0
- package/dist/shell/render/diagnostic.js.map +1 -0
- package/dist/shell/render/finding.d.ts +15 -0
- package/dist/shell/render/finding.d.ts.map +1 -0
- package/dist/shell/render/finding.js +57 -0
- package/dist/shell/render/finding.js.map +1 -0
- package/dist/shell/render/gates.d.ts +3 -0
- package/dist/shell/render/gates.d.ts.map +1 -0
- package/dist/shell/render/gates.js +56 -0
- package/dist/shell/render/gates.js.map +1 -0
- package/dist/shell/render/init-hook-pack.d.ts +16 -0
- package/dist/shell/render/init-hook-pack.d.ts.map +1 -0
- package/dist/shell/render/init-hook-pack.js +206 -0
- package/dist/shell/render/init-hook-pack.js.map +1 -0
- package/dist/shell/render/init.d.ts +11 -0
- package/dist/shell/render/init.d.ts.map +1 -0
- package/dist/shell/render/init.js +32 -0
- package/dist/shell/render/init.js.map +1 -0
- package/dist/shell/render/status.d.ts +26 -0
- package/dist/shell/render/status.d.ts.map +1 -0
- package/dist/shell/render/status.js +143 -0
- package/dist/shell/render/status.js.map +1 -0
- package/dist/shell/render/waiver.d.ts +21 -0
- package/dist/shell/render/waiver.d.ts.map +1 -0
- package/dist/shell/render/waiver.js +94 -0
- package/dist/shell/render/waiver.js.map +1 -0
- package/dist/shell/rules.d.ts +37 -0
- package/dist/shell/rules.d.ts.map +1 -0
- package/dist/shell/rules.js +51 -0
- package/dist/shell/rules.js.map +1 -0
- package/dist/shell/session/actor.d.ts +14 -0
- package/dist/shell/session/actor.d.ts.map +1 -0
- package/dist/shell/session/actor.js +34 -0
- package/dist/shell/session/actor.js.map +1 -0
- package/dist/shell/session/resolve-session.d.ts +5 -0
- package/dist/shell/session/resolve-session.d.ts.map +1 -0
- package/dist/shell/session/resolve-session.js +239 -0
- package/dist/shell/session/resolve-session.js.map +1 -0
- package/dist/shell/session/types.d.ts +56 -0
- package/dist/shell/session/types.d.ts.map +1 -0
- package/dist/shell/session/types.js +15 -0
- package/dist/shell/session/types.js.map +1 -0
- package/dist/store/agents-store.d.ts +3 -0
- package/dist/store/agents-store.d.ts.map +1 -0
- package/dist/store/agents-store.js +63 -0
- package/dist/store/agents-store.js.map +1 -0
- package/dist/store/apply-patch.d.ts +16 -0
- package/dist/store/apply-patch.d.ts.map +1 -0
- package/dist/store/apply-patch.js +191 -0
- package/dist/store/apply-patch.js.map +1 -0
- package/dist/store/atomic-write.d.ts +34 -0
- package/dist/store/atomic-write.d.ts.map +1 -0
- package/dist/store/atomic-write.js +174 -0
- package/dist/store/atomic-write.js.map +1 -0
- package/dist/store/doctor-snapshot.d.ts +20 -0
- package/dist/store/doctor-snapshot.d.ts.map +1 -0
- package/dist/store/doctor-snapshot.js +176 -0
- package/dist/store/doctor-snapshot.js.map +1 -0
- package/dist/store/events-store.d.ts +33 -0
- package/dist/store/events-store.d.ts.map +1 -0
- package/dist/store/events-store.js +297 -0
- package/dist/store/events-store.js.map +1 -0
- package/dist/store/index.d.ts +21 -0
- package/dist/store/index.d.ts.map +1 -0
- package/dist/store/index.js +47 -0
- package/dist/store/index.js.map +1 -0
- package/dist/store/init-store.d.ts +21 -0
- package/dist/store/init-store.d.ts.map +1 -0
- package/dist/store/init-store.js +295 -0
- package/dist/store/init-store.js.map +1 -0
- package/dist/store/json-store.d.ts +3 -0
- package/dist/store/json-store.d.ts.map +1 -0
- package/dist/store/json-store.js +65 -0
- package/dist/store/json-store.js.map +1 -0
- package/dist/store/lifecycle-lock.d.ts +34 -0
- package/dist/store/lifecycle-lock.d.ts.map +1 -0
- package/dist/store/lifecycle-lock.js +168 -0
- package/dist/store/lifecycle-lock.js.map +1 -0
- package/dist/store/lifecycle-transaction.d.ts +79 -0
- package/dist/store/lifecycle-transaction.d.ts.map +1 -0
- package/dist/store/lifecycle-transaction.js +319 -0
- package/dist/store/lifecycle-transaction.js.map +1 -0
- package/dist/store/policy-store.d.ts +3 -0
- package/dist/store/policy-store.d.ts.map +1 -0
- package/dist/store/policy-store.js +65 -0
- package/dist/store/policy-store.js.map +1 -0
- package/dist/store/repo-root.d.ts +46 -0
- package/dist/store/repo-root.d.ts.map +1 -0
- package/dist/store/repo-root.js +145 -0
- package/dist/store/repo-root.js.map +1 -0
- package/dist/store/rules.d.ts +69 -0
- package/dist/store/rules.d.ts.map +1 -0
- package/dist/store/rules.js +95 -0
- package/dist/store/rules.js.map +1 -0
- package/dist/store/specs-store.d.ts +3 -0
- package/dist/store/specs-store.d.ts.map +1 -0
- package/dist/store/specs-store.js +131 -0
- package/dist/store/specs-store.js.map +1 -0
- package/dist/store/specs-writer.d.ts +61 -0
- package/dist/store/specs-writer.d.ts.map +1 -0
- package/dist/store/specs-writer.js +506 -0
- package/dist/store/specs-writer.js.map +1 -0
- package/dist/store/types.d.ts +84 -0
- package/dist/store/types.d.ts.map +1 -0
- package/dist/store/types.js +14 -0
- package/dist/store/types.js.map +1 -0
- package/dist/store/waivers-store.d.ts +25 -0
- package/dist/store/waivers-store.d.ts.map +1 -0
- package/dist/store/waivers-store.js +232 -0
- package/dist/store/waivers-store.js.map +1 -0
- package/dist/store/worktrees-store.d.ts +3 -0
- package/dist/store/worktrees-store.d.ts.map +1 -0
- package/dist/store/worktrees-store.js +62 -0
- package/dist/store/worktrees-store.js.map +1 -0
- package/dist/store/worktrees-writer.d.ts +77 -0
- package/dist/store/worktrees-writer.d.ts.map +1 -0
- package/dist/store/worktrees-writer.js +674 -0
- package/dist/store/worktrees-writer.js.map +1 -0
- package/dist/store/yaml-patch.d.ts +7 -0
- package/dist/store/yaml-patch.d.ts.map +1 -0
- package/dist/store/yaml-patch.js +250 -0
- package/dist/store/yaml-patch.js.map +1 -0
- package/dist/store/yaml-store.d.ts +9 -0
- package/dist/store/yaml-store.d.ts.map +1 -0
- package/dist/store/yaml-store.js +121 -0
- package/dist/store/yaml-store.js.map +1 -0
- package/package.json +15 -13
- package/dist/budget-derivation.js +0 -751
- package/dist/cicd-optimizer.js +0 -504
- package/dist/commands/agents.js +0 -124
- package/dist/commands/archive.js +0 -500
- package/dist/commands/burnup.js +0 -198
- package/dist/commands/diagnose.js +0 -525
- package/dist/commands/evaluate.js +0 -314
- package/dist/commands/gates.js +0 -149
- package/dist/commands/init.js +0 -857
- package/dist/commands/iterate.js +0 -417
- package/dist/commands/mode.js +0 -269
- package/dist/commands/parallel.js +0 -242
- package/dist/commands/plan.js +0 -438
- package/dist/commands/provenance.js +0 -1143
- package/dist/commands/quality-monitor.js +0 -284
- package/dist/commands/scope.js +0 -264
- package/dist/commands/session.js +0 -312
- package/dist/commands/sidecar.js +0 -74
- package/dist/commands/specs.js +0 -1656
- package/dist/commands/status.js +0 -1172
- package/dist/commands/templates.js +0 -237
- package/dist/commands/tool.js +0 -136
- package/dist/commands/tutorial.js +0 -480
- package/dist/commands/validate.js +0 -357
- package/dist/commands/verify-acs.js +0 -443
- package/dist/commands/waivers.js +0 -599
- package/dist/commands/workflow.js +0 -243
- package/dist/commands/worktree.js +0 -502
- package/dist/config/lite-scope.js +0 -158
- package/dist/config/modes.js +0 -347
- package/dist/constants/spec-types.js +0 -65
- package/dist/gates/budget-limit.js +0 -121
- package/dist/gates/feedback.js +0 -260
- package/dist/gates/format.js +0 -179
- package/dist/gates/god-object.js +0 -117
- package/dist/gates/pipeline.js +0 -167
- package/dist/gates/scope-boundary.js +0 -112
- package/dist/gates/spec-completeness.js +0 -109
- package/dist/gates/todo-detection.js +0 -205
- package/dist/generators/jest-config-generator.js +0 -242
- package/dist/generators/working-spec.js +0 -237
- package/dist/minimal-cli.js +0 -88
- package/dist/parallel/parallel-manager.js +0 -433
- package/dist/policy/PolicyManager.js +0 -470
- package/dist/scaffold/claude-hooks.js +0 -443
- package/dist/scaffold/cursor-hooks.js +0 -177
- package/dist/scaffold/git-hooks.js +0 -928
- package/dist/scaffold/index.js +0 -794
- package/dist/session/session-manager.js +0 -653
- package/dist/sidecars/index.js +0 -33
- package/dist/sidecars/listeners.js +0 -40
- package/dist/sidecars/provenance-summary.js +0 -238
- package/dist/sidecars/quality-gaps.js +0 -258
- package/dist/sidecars/schema.js +0 -149
- package/dist/sidecars/spec-drift.js +0 -151
- package/dist/sidecars/waiver-draft.js +0 -176
- package/dist/spec/SpecFileManager.js +0 -419
- package/dist/templates/.caws/schemas/policy.schema.json +0 -117
- package/dist/templates/.caws/schemas/scope.schema.json +0 -52
- package/dist/templates/.caws/schemas/waivers.schema.json +0 -106
- package/dist/templates/.caws/schemas/working-spec.schema.json +0 -340
- package/dist/templates/.caws/schemas/worktrees.schema.json +0 -38
- package/dist/templates/.caws/templates/working-spec.template.yml +0 -80
- package/dist/templates/.caws/tools/README.md +0 -18
- package/dist/templates/.caws/tools/scope-guard.js +0 -203
- package/dist/templates/.caws/tools-allow.json +0 -331
- package/dist/templates/.caws/waivers.yml +0 -19
- package/dist/templates/.claude/README.md +0 -190
- package/dist/templates/.claude/hooks/audit.sh +0 -121
- package/dist/templates/.claude/hooks/block-dangerous.sh +0 -203
- package/dist/templates/.claude/hooks/classify_command.py +0 -592
- package/dist/templates/.claude/hooks/doc-frontmatter-check.sh +0 -173
- package/dist/templates/.claude/hooks/lite-sprawl-check.sh +0 -145
- package/dist/templates/.claude/hooks/naming-check.sh +0 -100
- package/dist/templates/.claude/hooks/protected-paths.sh +0 -39
- package/dist/templates/.claude/hooks/quality-check.sh +0 -81
- package/dist/templates/.claude/hooks/scan-secrets.sh +0 -85
- package/dist/templates/.claude/hooks/scope-guard.sh +0 -381
- package/dist/templates/.claude/hooks/session-caws-status.sh +0 -117
- package/dist/templates/.claude/hooks/session-log.sh +0 -634
- package/dist/templates/.claude/hooks/simplification-guard.sh +0 -92
- package/dist/templates/.claude/hooks/stop-worktree-check.sh +0 -46
- package/dist/templates/.claude/hooks/test_classify_command.py +0 -370
- package/dist/templates/.claude/hooks/test_wrapper_smoke.sh +0 -96
- package/dist/templates/.claude/hooks/validate-spec.sh +0 -76
- package/dist/templates/.claude/hooks/worktree-guard.sh +0 -220
- package/dist/templates/.claude/hooks/worktree-write-guard.sh +0 -190
- package/dist/templates/.claude/rules/git-safety.md +0 -26
- package/dist/templates/.claude/rules/worktree-isolation.md +0 -101
- package/dist/templates/.claude/settings.json +0 -141
- package/dist/templates/.cursor/README.md +0 -299
- package/dist/templates/.cursor/hooks/audit.sh +0 -55
- package/dist/templates/.cursor/hooks/block-dangerous.sh +0 -84
- package/dist/templates/.cursor/hooks/caws-quality-check.sh +0 -52
- package/dist/templates/.cursor/hooks/caws-scope-guard.sh +0 -130
- package/dist/templates/.cursor/hooks/format.sh +0 -38
- package/dist/templates/.cursor/hooks/naming-check.sh +0 -64
- package/dist/templates/.cursor/hooks/scan-secrets.sh +0 -51
- package/dist/templates/.cursor/hooks/scope-guard.sh +0 -52
- package/dist/templates/.cursor/hooks/session-log.sh +0 -924
- package/dist/templates/.cursor/hooks/validate-spec.sh +0 -83
- package/dist/templates/.cursor/hooks.json +0 -76
- package/dist/templates/.cursor/rules/00-claims-verification.mdc +0 -144
- package/dist/templates/.cursor/rules/01-working-style.mdc +0 -50
- package/dist/templates/.cursor/rules/02-quality-gates.mdc +0 -368
- package/dist/templates/.cursor/rules/03-naming-and-refactor.mdc +0 -33
- package/dist/templates/.cursor/rules/04-logging-language-style.mdc +0 -23
- package/dist/templates/.cursor/rules/05-safe-defaults-guards.mdc +0 -23
- package/dist/templates/.cursor/rules/06-typescript-conventions.mdc +0 -36
- package/dist/templates/.cursor/rules/07-process-ops.mdc +0 -20
- package/dist/templates/.cursor/rules/08-solid-and-architecture.mdc +0 -16
- package/dist/templates/.cursor/rules/09-docstrings.mdc +0 -89
- package/dist/templates/.cursor/rules/10-documentation-quality-standards.mdc +0 -385
- package/dist/templates/.cursor/rules/11-scope-management-waivers.mdc +0 -381
- package/dist/templates/.cursor/rules/12-implementation-completeness.mdc +0 -516
- package/dist/templates/.cursor/rules/13-language-agnostic-standards.mdc +0 -578
- package/dist/templates/.cursor/rules/README.md +0 -148
- package/dist/templates/.github/copilot-instructions.md +0 -82
- package/dist/templates/.idea/runConfigurations/CAWS_Evaluate.xml +0 -5
- package/dist/templates/.idea/runConfigurations/CAWS_Validate.xml +0 -5
- package/dist/templates/.junie/guidelines.md +0 -73
- package/dist/templates/.vscode/launch.json +0 -17
- package/dist/templates/.vscode/settings.json +0 -95
- package/dist/templates/.windsurf/rules/caws-quality-standards.md +0 -54
- package/dist/templates/.windsurf/workflows/caws-guided-development.md +0 -92
- package/dist/templates/CLAUDE.md +0 -196
- package/dist/templates/COMMIT_CONVENTIONS.md +0 -86
- package/dist/templates/OIDC_SETUP.md +0 -300
- package/dist/templates/agents.md +0 -171
- package/dist/templates/codemod/README.md +0 -1
- package/dist/templates/codemod/test.js +0 -93
- package/dist/templates/docs/README.md +0 -151
- package/dist/templates/scripts/new_feature.sh +0 -80
- package/dist/templates/scripts/quality-gates/check-god-objects.js +0 -146
- package/dist/templates/scripts/quality-gates/run-quality-gates.js +0 -50
- package/dist/templates/scripts/v3/analysis/todo_analyzer.py +0 -1997
- package/dist/test-analysis.js +0 -786
- package/dist/tool-interface.js +0 -314
- package/dist/tool-loader.js +0 -303
- package/dist/tool-validator.js +0 -393
- package/dist/utils/agent-display.js +0 -210
- package/dist/utils/agent-session.js +0 -344
- package/dist/utils/async-utils.js +0 -188
- package/dist/utils/command-wrapper.js +0 -200
- package/dist/utils/event-log.js +0 -584
- package/dist/utils/event-renderer.js +0 -521
- package/dist/utils/finalization.js +0 -230
- package/dist/utils/git-lock.js +0 -119
- package/dist/utils/gitignore-updater.js +0 -158
- package/dist/utils/ide-detection.js +0 -133
- package/dist/utils/lifecycle-events.js +0 -94
- package/dist/utils/project-analysis.js +0 -367
- package/dist/utils/promise-utils.js +0 -72
- package/dist/utils/quality-gates-errors.js +0 -520
- package/dist/utils/quality-gates-utils.js +0 -387
- package/dist/utils/schema-validator.js +0 -50
- package/dist/utils/spec-resolver.js +0 -711
- package/dist/utils/typescript-detector.js +0 -369
- package/dist/utils/working-state.js +0 -530
- package/dist/utils/yaml-validation.js +0 -156
- package/dist/validation/spec-validation.js +0 -924
- package/dist/waivers-manager.js +0 -732
- package/dist/worktree/worktree-manager.js +0 -1735
- package/templates/.caws/schemas/policy.schema.json +0 -117
- package/templates/.caws/schemas/scope.schema.json +0 -52
- package/templates/.caws/schemas/waivers.schema.json +0 -106
- package/templates/.caws/schemas/working-spec.schema.json +0 -340
- package/templates/.caws/schemas/worktrees.schema.json +0 -38
- package/templates/.caws/templates/working-spec.template.yml +0 -80
- package/templates/.caws/tools/README.md +0 -18
- package/templates/.caws/tools/scope-guard.js +0 -203
- package/templates/.caws/tools-allow.json +0 -331
- package/templates/.caws/waivers.yml +0 -19
- package/templates/.claude/README.md +0 -190
- package/templates/.claude/hooks/audit.sh +0 -121
- package/templates/.claude/hooks/block-dangerous.sh +0 -203
- package/templates/.claude/hooks/classify_command.py +0 -592
- package/templates/.claude/hooks/doc-frontmatter-check.sh +0 -173
- package/templates/.claude/hooks/lite-sprawl-check.sh +0 -145
- package/templates/.claude/hooks/naming-check.sh +0 -100
- package/templates/.claude/hooks/protected-paths.sh +0 -39
- package/templates/.claude/hooks/quality-check.sh +0 -81
- package/templates/.claude/hooks/scan-secrets.sh +0 -85
- package/templates/.claude/hooks/scope-guard.sh +0 -381
- package/templates/.claude/hooks/session-caws-status.sh +0 -117
- package/templates/.claude/hooks/session-log.sh +0 -634
- package/templates/.claude/hooks/simplification-guard.sh +0 -92
- package/templates/.claude/hooks/stop-worktree-check.sh +0 -46
- package/templates/.claude/hooks/test_classify_command.py +0 -370
- package/templates/.claude/hooks/test_wrapper_smoke.sh +0 -96
- package/templates/.claude/hooks/validate-spec.sh +0 -76
- package/templates/.claude/hooks/worktree-guard.sh +0 -220
- package/templates/.claude/hooks/worktree-write-guard.sh +0 -190
- package/templates/.claude/rules/git-safety.md +0 -26
- package/templates/.claude/rules/worktree-isolation.md +0 -101
- package/templates/.claude/settings.json +0 -141
- package/templates/.cursor/README.md +0 -299
- package/templates/.cursor/hooks/audit.sh +0 -55
- package/templates/.cursor/hooks/block-dangerous.sh +0 -84
- package/templates/.cursor/hooks/caws-quality-check.sh +0 -52
- package/templates/.cursor/hooks/caws-scope-guard.sh +0 -130
- package/templates/.cursor/hooks/format.sh +0 -38
- package/templates/.cursor/hooks/naming-check.sh +0 -64
- package/templates/.cursor/hooks/scan-secrets.sh +0 -51
- package/templates/.cursor/hooks/scope-guard.sh +0 -52
- package/templates/.cursor/hooks/session-log.sh +0 -924
- package/templates/.cursor/hooks/validate-spec.sh +0 -83
- package/templates/.cursor/hooks.json +0 -76
- package/templates/.cursor/rules/00-claims-verification.mdc +0 -144
- package/templates/.cursor/rules/01-working-style.mdc +0 -50
- package/templates/.cursor/rules/02-quality-gates.mdc +0 -368
- package/templates/.cursor/rules/03-naming-and-refactor.mdc +0 -33
- package/templates/.cursor/rules/04-logging-language-style.mdc +0 -23
- package/templates/.cursor/rules/05-safe-defaults-guards.mdc +0 -23
- package/templates/.cursor/rules/06-typescript-conventions.mdc +0 -36
- package/templates/.cursor/rules/07-process-ops.mdc +0 -20
- package/templates/.cursor/rules/08-solid-and-architecture.mdc +0 -16
- package/templates/.cursor/rules/09-docstrings.mdc +0 -89
- package/templates/.cursor/rules/10-documentation-quality-standards.mdc +0 -385
- package/templates/.cursor/rules/11-scope-management-waivers.mdc +0 -381
- package/templates/.cursor/rules/12-implementation-completeness.mdc +0 -516
- package/templates/.cursor/rules/13-language-agnostic-standards.mdc +0 -578
- package/templates/.cursor/rules/README.md +0 -148
- package/templates/.github/copilot-instructions.md +0 -82
- package/templates/.idea/runConfigurations/CAWS_Evaluate.xml +0 -5
- package/templates/.idea/runConfigurations/CAWS_Validate.xml +0 -5
- package/templates/.junie/guidelines.md +0 -73
- package/templates/.vscode/launch.json +0 -17
- package/templates/.vscode/settings.json +0 -95
- package/templates/.windsurf/rules/caws-quality-standards.md +0 -54
- package/templates/.windsurf/workflows/caws-guided-development.md +0 -92
- package/templates/CLAUDE.md +0 -196
- package/templates/COMMIT_CONVENTIONS.md +0 -86
- package/templates/OIDC_SETUP.md +0 -300
- package/templates/agents.md +0 -171
- package/templates/codemod/README.md +0 -1
- package/templates/codemod/test.js +0 -93
- package/templates/docs/README.md +0 -151
- package/templates/scripts/new_feature.sh +0 -80
- package/templates/scripts/quality-gates/check-god-objects.js +0 -146
- package/templates/scripts/quality-gates/run-quality-gates.js +0 -50
- package/templates/scripts/v3/analysis/todo_analyzer.py +0 -1997
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import { type ChainedEvent, type EventBody, type Result, type Diagnostic } from '@paths.design/caws-kernel';
|
|
2
|
+
/** A single file write the transaction will perform. Order in
|
|
3
|
+
* `plannedWrites` is the order writes are applied. */
|
|
4
|
+
export interface LifecycleFileWrite {
|
|
5
|
+
/** Absolute path of the file to write. */
|
|
6
|
+
readonly path: string;
|
|
7
|
+
/** New contents for this file. */
|
|
8
|
+
readonly contents: string | Buffer;
|
|
9
|
+
/** When true, writeFileAtomic preserves the target's existing mode. */
|
|
10
|
+
readonly preserveMode?: boolean;
|
|
11
|
+
}
|
|
12
|
+
/** Inputs to a lifecycle transaction. */
|
|
13
|
+
export interface LifecycleTransactionPlan {
|
|
14
|
+
/** Path to the .caws/ directory (passed through to appendEvent). */
|
|
15
|
+
readonly cawsDir: string;
|
|
16
|
+
/** Files to write in deterministic order. */
|
|
17
|
+
readonly plannedWrites: readonly LifecycleFileWrite[];
|
|
18
|
+
/** Event(s) to append after state writes succeed. Appended in array
|
|
19
|
+
* order. The transaction supports multiple events per command (e.g.,
|
|
20
|
+
* worktree create emits worktree_created then worktree_bound). */
|
|
21
|
+
readonly events: readonly EventBody[];
|
|
22
|
+
/** Optional pre-write validation. Runs AFTER the lock is held and
|
|
23
|
+
* files are read, BEFORE any write. Returns Err to abort the
|
|
24
|
+
* transaction with LIFECYCLE_PLAN_REJECTED. */
|
|
25
|
+
readonly validate?: () => Result<void>;
|
|
26
|
+
/** When true, call fsyncDir on each affected directory after writes.
|
|
27
|
+
* Defaults to false; see module header for rationale. */
|
|
28
|
+
readonly fsyncAfter?: boolean;
|
|
29
|
+
}
|
|
30
|
+
/** Success outcome: all state writes + all event appends succeeded. */
|
|
31
|
+
export interface LifecycleTransactionSuccess {
|
|
32
|
+
readonly kind: 'success';
|
|
33
|
+
readonly writes: readonly {
|
|
34
|
+
readonly path: string;
|
|
35
|
+
}[];
|
|
36
|
+
readonly appendedEvents: readonly ChainedEvent[];
|
|
37
|
+
}
|
|
38
|
+
/** Partial-failure-recovered: state writes succeeded, event append
|
|
39
|
+
* failed, rollback succeeded. The repository is in its pre-transaction
|
|
40
|
+
* state. */
|
|
41
|
+
export interface LifecyclePartialRecovered {
|
|
42
|
+
readonly kind: 'partial_failure_recovered';
|
|
43
|
+
readonly cause: readonly Diagnostic[];
|
|
44
|
+
readonly rolledBack: readonly string[];
|
|
45
|
+
}
|
|
46
|
+
/** Partial-failure-unrecovered: state writes succeeded, event append
|
|
47
|
+
* failed, AND rollback also failed. The repository may be in a
|
|
48
|
+
* partial state. The caller MUST handle the recovery instruction. */
|
|
49
|
+
export interface LifecyclePartialUnrecovered {
|
|
50
|
+
readonly kind: 'partial_failure_unrecovered';
|
|
51
|
+
readonly cause: readonly Diagnostic[];
|
|
52
|
+
readonly plannedEvents: readonly EventBody[];
|
|
53
|
+
readonly writesCompleted: readonly string[];
|
|
54
|
+
readonly rolledBack: readonly string[];
|
|
55
|
+
readonly rollbackFailed: readonly {
|
|
56
|
+
readonly path: string;
|
|
57
|
+
readonly reason: string;
|
|
58
|
+
}[];
|
|
59
|
+
readonly recoveryInstruction: string;
|
|
60
|
+
}
|
|
61
|
+
export type LifecycleTransactionResult = LifecycleTransactionSuccess | LifecyclePartialRecovered | LifecyclePartialUnrecovered;
|
|
62
|
+
/**
|
|
63
|
+
* Run a lifecycle transaction.
|
|
64
|
+
*
|
|
65
|
+
* The caller MUST hold the lifecycle lock (via withLifecycleLock or
|
|
66
|
+
* acquireLifecycleLock). This function does not acquire the lock
|
|
67
|
+
* itself; that responsibility lives in the caller so a higher-level
|
|
68
|
+
* orchestrator (CLI-SPECS-001, CLI-WORKTREE-001) can group multiple
|
|
69
|
+
* conceptual mutations inside one lock if needed.
|
|
70
|
+
*
|
|
71
|
+
* Returns:
|
|
72
|
+
* Ok({ kind: 'success', ... }) — everything worked
|
|
73
|
+
* Ok({ kind: 'partial_failure_recovered', ... }) — rolled back cleanly
|
|
74
|
+
* Err([LIFECYCLE_PARTIAL_FAILURE_UNRECOVERED]) — partial state remains
|
|
75
|
+
* Err([LIFECYCLE_PLAN_REJECTED]) — validate() rejected
|
|
76
|
+
* Err([LIFECYCLE_WRITE_FAILED]) — a write failed before events
|
|
77
|
+
*/
|
|
78
|
+
export declare function runLifecycleTransaction(plan: LifecycleTransactionPlan): Result<LifecycleTransactionResult>;
|
|
79
|
+
//# sourceMappingURL=lifecycle-transaction.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lifecycle-transaction.d.ts","sourceRoot":"","sources":["../../src/store/lifecycle-transaction.ts"],"names":[],"mappings":"AAuCA,OAAO,EACL,KAAK,YAAY,EACjB,KAAK,SAAS,EAGd,KAAK,MAAM,EACX,KAAK,UAAU,EAChB,MAAM,2BAA2B,CAAC;AASnC;uDACuD;AACvD,MAAM,WAAW,kBAAkB;IACjC,0CAA0C;IAC1C,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,kCAAkC;IAClC,QAAQ,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAAC;IACnC,uEAAuE;IACvE,QAAQ,CAAC,YAAY,CAAC,EAAE,OAAO,CAAC;CACjC;AAED,yCAAyC;AACzC,MAAM,WAAW,wBAAwB;IACvC,oEAAoE;IACpE,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,6CAA6C;IAC7C,QAAQ,CAAC,aAAa,EAAE,SAAS,kBAAkB,EAAE,CAAC;IACtD;;uEAEmE;IACnE,QAAQ,CAAC,MAAM,EAAE,SAAS,SAAS,EAAE,CAAC;IACtC;;oDAEgD;IAChD,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,MAAM,CAAC,IAAI,CAAC,CAAC;IACvC;8DAC0D;IAC1D,QAAQ,CAAC,UAAU,CAAC,EAAE,OAAO,CAAC;CAC/B;AAWD,uEAAuE;AACvE,MAAM,WAAW,2BAA2B;IAC1C,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC;IACzB,QAAQ,CAAC,MAAM,EAAE,SAAS;QAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;KAAE,EAAE,CAAC;IACtD,QAAQ,CAAC,cAAc,EAAE,SAAS,YAAY,EAAE,CAAC;CAClD;AAED;;aAEa;AACb,MAAM,WAAW,yBAAyB;IACxC,QAAQ,CAAC,IAAI,EAAE,2BAA2B,CAAC;IAC3C,QAAQ,CAAC,KAAK,EAAE,SAAS,UAAU,EAAE,CAAC;IACtC,QAAQ,CAAC,UAAU,EAAE,SAAS,MAAM,EAAE,CAAC;CACxC;AAED;;sEAEsE;AACtE,MAAM,WAAW,2BAA2B;IAC1C,QAAQ,CAAC,IAAI,EAAE,6BAA6B,CAAC;IAC7C,QAAQ,CAAC,KAAK,EAAE,SAAS,UAAU,EAAE,CAAC;IACtC,QAAQ,CAAC,aAAa,EAAE,SAAS,SAAS,EAAE,CAAC;IAC7C,QAAQ,CAAC,eAAe,EAAE,SAAS,MAAM,EAAE,CAAC;IAC5C,QAAQ,CAAC,UAAU,EAAE,SAAS,MAAM,EAAE,CAAC;IACvC,QAAQ,CAAC,cAAc,EAAE,SAAS;QAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;QAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;KAAE,EAAE,CAAC;IACvF,QAAQ,CAAC,mBAAmB,EAAE,MAAM,CAAC;CACtC;AAED,MAAM,MAAM,0BAA0B,GAClC,2BAA2B,GAC3B,yBAAyB,GACzB,2BAA2B,CAAC;AAkGhC;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,uBAAuB,CACrC,IAAI,EAAE,wBAAwB,GAC7B,MAAM,CAAC,0BAA0B,CAAC,CA+JpC"}
|
|
@@ -0,0 +1,319 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// Lifecycle mutation transaction wrapper.
|
|
3
|
+
//
|
|
4
|
+
// LIFECYCLE-MUTATION-001 substrate: multi-file lifecycle mutations
|
|
5
|
+
// serialize through .caws/state.lock and produce a typed outcome that
|
|
6
|
+
// names partial-failure explicitly. The transaction is NOT a database
|
|
7
|
+
// transaction — filesystem rollback is best-effort, and the useful
|
|
8
|
+
// invariant is "partial failure is detected, named, and recoverable,"
|
|
9
|
+
// not "rollback always succeeds."
|
|
10
|
+
//
|
|
11
|
+
// Operation order (within the critical section):
|
|
12
|
+
// 1. acquire lifecycle lock (already done by withLifecycleLock or
|
|
13
|
+
// directly by the caller)
|
|
14
|
+
// 2. read all affected files; capture original bytes for rollback
|
|
15
|
+
// 3. compute planned writes (caller-provided)
|
|
16
|
+
// 4. validate planned state via kernel hooks (caller-provided)
|
|
17
|
+
// 5. write files in deterministic order using writeFileAtomic
|
|
18
|
+
// with preserveMode: true (per A2)
|
|
19
|
+
// 6. append the transaction's event(s) through appendEvent (the SOLE
|
|
20
|
+
// v11 writer of events.jsonl)
|
|
21
|
+
// 7. if event append fails, attempt rollback of all written files
|
|
22
|
+
// from captured original bytes; produce LIFECYCLE_PARTIAL_FAILURE_*
|
|
23
|
+
// 8. release lock (caller's `finally`)
|
|
24
|
+
//
|
|
25
|
+
// fsyncDir posture (A3):
|
|
26
|
+
// This module does NOT call fsyncDir by default. Rationale: v11.1
|
|
27
|
+
// accepts rename durability without parent-directory fsync for two
|
|
28
|
+
// reasons. (a) writeFileAtomic already does file-content fsync before
|
|
29
|
+
// rename, which is the durability primitive that survives kernel
|
|
30
|
+
// crashes; only power loss between rename and dirent flush is at risk.
|
|
31
|
+
// (b) The lock + event-append step provides a recovery anchor: if a
|
|
32
|
+
// crash leaves the filesystem in a partially-renamed state, the next
|
|
33
|
+
// transaction's read step will see whichever state the filesystem
|
|
34
|
+
// committed, and the event log's last entry tells the operator the
|
|
35
|
+
// last fully-acknowledged transition. Power-loss safety is therefore
|
|
36
|
+
// bounded by the audit log, not by directory fsync. Callers needing
|
|
37
|
+
// stronger durability may pass an `fsyncAfter: true` option.
|
|
38
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
39
|
+
if (k2 === undefined) k2 = k;
|
|
40
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
41
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
42
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
43
|
+
}
|
|
44
|
+
Object.defineProperty(o, k2, desc);
|
|
45
|
+
}) : (function(o, m, k, k2) {
|
|
46
|
+
if (k2 === undefined) k2 = k;
|
|
47
|
+
o[k2] = m[k];
|
|
48
|
+
}));
|
|
49
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
50
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
51
|
+
}) : function(o, v) {
|
|
52
|
+
o["default"] = v;
|
|
53
|
+
});
|
|
54
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
55
|
+
var ownKeys = function(o) {
|
|
56
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
57
|
+
var ar = [];
|
|
58
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
59
|
+
return ar;
|
|
60
|
+
};
|
|
61
|
+
return ownKeys(o);
|
|
62
|
+
};
|
|
63
|
+
return function (mod) {
|
|
64
|
+
if (mod && mod.__esModule) return mod;
|
|
65
|
+
var result = {};
|
|
66
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
67
|
+
__setModuleDefault(result, mod);
|
|
68
|
+
return result;
|
|
69
|
+
};
|
|
70
|
+
})();
|
|
71
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
72
|
+
exports.runLifecycleTransaction = runLifecycleTransaction;
|
|
73
|
+
const fs = __importStar(require("fs"));
|
|
74
|
+
const caws_kernel_1 = require("@paths.design/caws-kernel");
|
|
75
|
+
const atomic_write_1 = require("./atomic-write");
|
|
76
|
+
const events_store_1 = require("./events-store");
|
|
77
|
+
const repo_root_1 = require("./repo-root");
|
|
78
|
+
const rules_1 = require("./rules");
|
|
79
|
+
// ─── Implementation ──────────────────────────────────────────────────────
|
|
80
|
+
function captureSnapshot(filePath) {
|
|
81
|
+
try {
|
|
82
|
+
const stat = fs.statSync(filePath);
|
|
83
|
+
const originalContents = fs.readFileSync(filePath);
|
|
84
|
+
return {
|
|
85
|
+
path: filePath,
|
|
86
|
+
originalContents,
|
|
87
|
+
originalMode: stat.mode & 0o7777,
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
catch (e) {
|
|
91
|
+
const cause = e;
|
|
92
|
+
if (cause.code === 'ENOENT') {
|
|
93
|
+
return { path: filePath, originalContents: null, originalMode: undefined };
|
|
94
|
+
}
|
|
95
|
+
// Any other read failure: surface as a snapshot we don't trust.
|
|
96
|
+
// Treat as "file did not exist" for rollback purposes; the
|
|
97
|
+
// transaction's write step will hit the same error and abort.
|
|
98
|
+
return { path: filePath, originalContents: null, originalMode: undefined };
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
function rollbackOne(snapshot) {
|
|
102
|
+
try {
|
|
103
|
+
if (snapshot.originalContents === null) {
|
|
104
|
+
// File didn't exist before; rollback is to delete it.
|
|
105
|
+
try {
|
|
106
|
+
fs.unlinkSync(snapshot.path);
|
|
107
|
+
}
|
|
108
|
+
catch (e) {
|
|
109
|
+
const cause = e;
|
|
110
|
+
// Already gone — treat as success.
|
|
111
|
+
if (cause.code === 'ENOENT')
|
|
112
|
+
return { ok: true };
|
|
113
|
+
return { ok: false, reason: `failed to remove ${snapshot.path}: ${cause.code ?? 'unknown'}` };
|
|
114
|
+
}
|
|
115
|
+
return { ok: true };
|
|
116
|
+
}
|
|
117
|
+
// Restore prior contents. Use writeFileAtomic with the captured
|
|
118
|
+
// mode so the rollback itself is atomic at the file level.
|
|
119
|
+
const opts = snapshot.originalMode !== undefined ? { preserveMode: true } : {};
|
|
120
|
+
// Pre-stage the target file with original mode by chmod-then-write
|
|
121
|
+
// is overkill; writeFileAtomic with preserveMode will stat the
|
|
122
|
+
// target (which currently has the failed-transaction bytes and
|
|
123
|
+
// possibly a different mode). Safer: write first with default
|
|
124
|
+
// mode, then chmod explicitly.
|
|
125
|
+
const writeResult = (0, atomic_write_1.writeFileAtomic)(snapshot.path, snapshot.originalContents, opts);
|
|
126
|
+
if (!writeResult.ok) {
|
|
127
|
+
return { ok: false, reason: `writeFileAtomic failed during rollback: ${snapshot.path}` };
|
|
128
|
+
}
|
|
129
|
+
if (snapshot.originalMode !== undefined) {
|
|
130
|
+
try {
|
|
131
|
+
fs.chmodSync(snapshot.path, snapshot.originalMode);
|
|
132
|
+
}
|
|
133
|
+
catch {
|
|
134
|
+
// Mode-restore failure during rollback: contents are restored
|
|
135
|
+
// but mode may be wrong. We do NOT escalate to unrecovered for
|
|
136
|
+
// a mode-only failure; the file content is correct.
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
return { ok: true };
|
|
140
|
+
}
|
|
141
|
+
catch (e) {
|
|
142
|
+
const cause = e;
|
|
143
|
+
return { ok: false, reason: cause.message ?? 'unknown rollback error' };
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
function buildRecoveryInstruction(plannedEvents, writesCompleted, rolledBack, rollbackFailed) {
|
|
147
|
+
const lines = [
|
|
148
|
+
'Lifecycle transaction left the repository in a partial state.',
|
|
149
|
+
` ${writesCompleted.length} file write(s) completed before failure.`,
|
|
150
|
+
` ${rolledBack.length} successfully rolled back; ${rollbackFailed.length} rollback failure(s).`,
|
|
151
|
+
'',
|
|
152
|
+
`Files that may need manual inspection:`,
|
|
153
|
+
];
|
|
154
|
+
for (const f of rollbackFailed) {
|
|
155
|
+
lines.push(` ${f.path} (rollback failed)`);
|
|
156
|
+
}
|
|
157
|
+
lines.push('');
|
|
158
|
+
lines.push(`Events that were NOT appended (${plannedEvents.length}):`);
|
|
159
|
+
for (const ev of plannedEvents) {
|
|
160
|
+
lines.push(` ${ev.event} (spec_id=${ev.spec_id ?? 'n/a'})`);
|
|
161
|
+
}
|
|
162
|
+
lines.push('');
|
|
163
|
+
lines.push('Required action: review each listed file against the planned event payload above to');
|
|
164
|
+
lines.push('determine whether to redo the lifecycle transition or to manually restore prior state.');
|
|
165
|
+
lines.push('Do NOT hand-author entries into events.jsonl.');
|
|
166
|
+
return lines.join('\n');
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Run a lifecycle transaction.
|
|
170
|
+
*
|
|
171
|
+
* The caller MUST hold the lifecycle lock (via withLifecycleLock or
|
|
172
|
+
* acquireLifecycleLock). This function does not acquire the lock
|
|
173
|
+
* itself; that responsibility lives in the caller so a higher-level
|
|
174
|
+
* orchestrator (CLI-SPECS-001, CLI-WORKTREE-001) can group multiple
|
|
175
|
+
* conceptual mutations inside one lock if needed.
|
|
176
|
+
*
|
|
177
|
+
* Returns:
|
|
178
|
+
* Ok({ kind: 'success', ... }) — everything worked
|
|
179
|
+
* Ok({ kind: 'partial_failure_recovered', ... }) — rolled back cleanly
|
|
180
|
+
* Err([LIFECYCLE_PARTIAL_FAILURE_UNRECOVERED]) — partial state remains
|
|
181
|
+
* Err([LIFECYCLE_PLAN_REJECTED]) — validate() rejected
|
|
182
|
+
* Err([LIFECYCLE_WRITE_FAILED]) — a write failed before events
|
|
183
|
+
*/
|
|
184
|
+
function runLifecycleTransaction(plan) {
|
|
185
|
+
// Step 1: validate plan (pre-write).
|
|
186
|
+
if (plan.validate) {
|
|
187
|
+
const validation = plan.validate();
|
|
188
|
+
if (!validation.ok) {
|
|
189
|
+
const diagnostics = validation.errors.map((d) => {
|
|
190
|
+
const extra = {
|
|
191
|
+
data: { source_rule: d.rule },
|
|
192
|
+
};
|
|
193
|
+
if (d.subject !== undefined)
|
|
194
|
+
extra.subject = d.subject;
|
|
195
|
+
return (0, repo_root_1.storeDiagnostic)(rules_1.STORE_RULES.LIFECYCLE_PLAN_REJECTED, d.message, extra);
|
|
196
|
+
});
|
|
197
|
+
return (0, caws_kernel_1.err)(diagnostics);
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
// Step 2: snapshot every planned file BEFORE any write.
|
|
201
|
+
const snapshots = plan.plannedWrites.map((w) => captureSnapshot(w.path));
|
|
202
|
+
// Step 3: apply writes in deterministic order.
|
|
203
|
+
const writesCompleted = [];
|
|
204
|
+
for (let i = 0; i < plan.plannedWrites.length; i++) {
|
|
205
|
+
const w = plan.plannedWrites[i];
|
|
206
|
+
if (!w)
|
|
207
|
+
continue;
|
|
208
|
+
const opts = w.preserveMode === true ? { preserveMode: true } : {};
|
|
209
|
+
const result = (0, atomic_write_1.writeFileAtomic)(w.path, w.contents, opts);
|
|
210
|
+
if (!result.ok) {
|
|
211
|
+
// Write failed; the transaction has not yet appended any events.
|
|
212
|
+
// Roll back the writes that already succeeded.
|
|
213
|
+
const rolledBack = [];
|
|
214
|
+
const rollbackFailed = [];
|
|
215
|
+
for (let j = i - 1; j >= 0; j--) {
|
|
216
|
+
const snap = snapshots[j];
|
|
217
|
+
if (!snap)
|
|
218
|
+
continue;
|
|
219
|
+
const r = rollbackOne(snap);
|
|
220
|
+
if (r.ok)
|
|
221
|
+
rolledBack.push(snap.path);
|
|
222
|
+
else
|
|
223
|
+
rollbackFailed.push({ path: snap.path, reason: r.reason });
|
|
224
|
+
}
|
|
225
|
+
if (rollbackFailed.length === 0) {
|
|
226
|
+
const diagnostics = result.errors.map((d) => {
|
|
227
|
+
const extra = {
|
|
228
|
+
data: { source_rule: d.rule, rolled_back: rolledBack.length },
|
|
229
|
+
};
|
|
230
|
+
if (d.subject !== undefined)
|
|
231
|
+
extra.subject = d.subject;
|
|
232
|
+
return (0, repo_root_1.storeDiagnostic)(rules_1.STORE_RULES.LIFECYCLE_WRITE_FAILED, d.message, extra);
|
|
233
|
+
});
|
|
234
|
+
return (0, caws_kernel_1.err)(diagnostics);
|
|
235
|
+
}
|
|
236
|
+
// Rollback during pre-event-write failure is itself unrecovered.
|
|
237
|
+
const recoveryInstruction = buildRecoveryInstruction(plan.events, writesCompleted, rolledBack, rollbackFailed);
|
|
238
|
+
return (0, caws_kernel_1.err)((0, repo_root_1.storeDiagnostic)(rules_1.STORE_RULES.LIFECYCLE_PARTIAL_FAILURE_UNRECOVERED, `Lifecycle write failed and rollback could not fully restore prior state.`, {
|
|
239
|
+
subject: w.path,
|
|
240
|
+
data: {
|
|
241
|
+
writes_completed: writesCompleted,
|
|
242
|
+
rolled_back: rolledBack,
|
|
243
|
+
rollback_failed: rollbackFailed,
|
|
244
|
+
recovery_instruction: recoveryInstruction,
|
|
245
|
+
},
|
|
246
|
+
}));
|
|
247
|
+
}
|
|
248
|
+
writesCompleted.push(w.path);
|
|
249
|
+
}
|
|
250
|
+
// Step 3b (optional): fsync affected directories.
|
|
251
|
+
if (plan.fsyncAfter === true) {
|
|
252
|
+
const dirs = new Set();
|
|
253
|
+
for (const w of plan.plannedWrites) {
|
|
254
|
+
const lastSlash = w.path.lastIndexOf('/');
|
|
255
|
+
if (lastSlash > 0)
|
|
256
|
+
dirs.add(w.path.slice(0, lastSlash));
|
|
257
|
+
}
|
|
258
|
+
for (const d of dirs) {
|
|
259
|
+
(0, atomic_write_1.fsyncDir)(d);
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
// Step 4: append events through appendEvent (the SOLE v11 events
|
|
263
|
+
// writer). On any failure, attempt rollback.
|
|
264
|
+
const appendedEvents = [];
|
|
265
|
+
for (let i = 0; i < plan.events.length; i++) {
|
|
266
|
+
const body = plan.events[i];
|
|
267
|
+
if (!body)
|
|
268
|
+
continue;
|
|
269
|
+
const result = (0, events_store_1.appendEvent)(plan.cawsDir, body);
|
|
270
|
+
if (!result.ok) {
|
|
271
|
+
// Roll back all writes. Reverse order so latest writes are
|
|
272
|
+
// restored to their pre-transaction state first.
|
|
273
|
+
const rolledBack = [];
|
|
274
|
+
const rollbackFailed = [];
|
|
275
|
+
for (let j = snapshots.length - 1; j >= 0; j--) {
|
|
276
|
+
const snap = snapshots[j];
|
|
277
|
+
if (!snap)
|
|
278
|
+
continue;
|
|
279
|
+
const r = rollbackOne(snap);
|
|
280
|
+
if (r.ok)
|
|
281
|
+
rolledBack.push(snap.path);
|
|
282
|
+
else
|
|
283
|
+
rollbackFailed.push({ path: snap.path, reason: r.reason });
|
|
284
|
+
}
|
|
285
|
+
// Also, previously-appended events in this transaction are
|
|
286
|
+
// already in the log. We CANNOT un-append from a hash-chained
|
|
287
|
+
// log without breaking the chain. Surface this in the recovery
|
|
288
|
+
// instruction.
|
|
289
|
+
if (rollbackFailed.length === 0 && appendedEvents.length === 0) {
|
|
290
|
+
return (0, caws_kernel_1.ok)({
|
|
291
|
+
kind: 'partial_failure_recovered',
|
|
292
|
+
cause: result.errors,
|
|
293
|
+
rolledBack,
|
|
294
|
+
});
|
|
295
|
+
}
|
|
296
|
+
const recoveryInstruction = buildRecoveryInstruction(plan.events, writesCompleted, rolledBack, rollbackFailed);
|
|
297
|
+
return (0, caws_kernel_1.err)((0, repo_root_1.storeDiagnostic)(rules_1.STORE_RULES.LIFECYCLE_PARTIAL_FAILURE_UNRECOVERED, `Lifecycle event append failed. ${appendedEvents.length} event(s) were already appended before the failure; ${rollbackFailed.length} file(s) could not be rolled back.`, {
|
|
298
|
+
subject: body.event,
|
|
299
|
+
data: {
|
|
300
|
+
writes_completed: writesCompleted,
|
|
301
|
+
rolled_back: rolledBack,
|
|
302
|
+
rollback_failed: rollbackFailed,
|
|
303
|
+
already_appended: appendedEvents.map((e) => ({
|
|
304
|
+
seq: e.seq,
|
|
305
|
+
event_hash: e.event_hash,
|
|
306
|
+
})),
|
|
307
|
+
recovery_instruction: recoveryInstruction,
|
|
308
|
+
},
|
|
309
|
+
}));
|
|
310
|
+
}
|
|
311
|
+
appendedEvents.push(result.value);
|
|
312
|
+
}
|
|
313
|
+
return (0, caws_kernel_1.ok)({
|
|
314
|
+
kind: 'success',
|
|
315
|
+
writes: writesCompleted.map((path) => ({ path })),
|
|
316
|
+
appendedEvents,
|
|
317
|
+
});
|
|
318
|
+
}
|
|
319
|
+
//# sourceMappingURL=lifecycle-transaction.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lifecycle-transaction.js","sourceRoot":"","sources":["../../src/store/lifecycle-transaction.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"policy-store.d.ts","sourceRoot":"","sources":["../../src/store/policy-store.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC;AAEhD,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,GAAG,gBAAgB,CAmB5D"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// Policy loader.
|
|
3
|
+
//
|
|
4
|
+
// Loads `.caws/policy.yaml`, hands the source to the kernel's
|
|
5
|
+
// `parseAndValidatePolicy`, and surfaces both the parsed value and any
|
|
6
|
+
// non-fatal warnings the kernel emitted. Missing file is NOT an error
|
|
7
|
+
// at the store level — doctor decides whether to emit `POLICY_MISSING`.
|
|
8
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
9
|
+
if (k2 === undefined) k2 = k;
|
|
10
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
11
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
12
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
13
|
+
}
|
|
14
|
+
Object.defineProperty(o, k2, desc);
|
|
15
|
+
}) : (function(o, m, k, k2) {
|
|
16
|
+
if (k2 === undefined) k2 = k;
|
|
17
|
+
o[k2] = m[k];
|
|
18
|
+
}));
|
|
19
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
20
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
21
|
+
}) : function(o, v) {
|
|
22
|
+
o["default"] = v;
|
|
23
|
+
});
|
|
24
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
25
|
+
var ownKeys = function(o) {
|
|
26
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
27
|
+
var ar = [];
|
|
28
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
29
|
+
return ar;
|
|
30
|
+
};
|
|
31
|
+
return ownKeys(o);
|
|
32
|
+
};
|
|
33
|
+
return function (mod) {
|
|
34
|
+
if (mod && mod.__esModule) return mod;
|
|
35
|
+
var result = {};
|
|
36
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
37
|
+
__setModuleDefault(result, mod);
|
|
38
|
+
return result;
|
|
39
|
+
};
|
|
40
|
+
})();
|
|
41
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
42
|
+
exports.loadPolicy = loadPolicy;
|
|
43
|
+
const path = __importStar(require("path"));
|
|
44
|
+
const caws_kernel_1 = require("@paths.design/caws-kernel");
|
|
45
|
+
const rules_1 = require("./rules");
|
|
46
|
+
const yaml_store_1 = require("./yaml-store");
|
|
47
|
+
function loadPolicy(cawsDir) {
|
|
48
|
+
const policyPath = path.join(cawsDir, 'policy.yaml');
|
|
49
|
+
const source = (0, yaml_store_1.readYamlSource)(policyPath);
|
|
50
|
+
if (!(0, caws_kernel_1.isOk)(source)) {
|
|
51
|
+
// Distinguish missing file (Ok-shaped) from malformed file (Err).
|
|
52
|
+
const missing = source.errors.some((e) => e.rule === rules_1.STORE_RULES.READ_MISSING_FILE);
|
|
53
|
+
if (missing) {
|
|
54
|
+
return { warnings: [], errors: [] };
|
|
55
|
+
}
|
|
56
|
+
return { warnings: [], errors: [...source.errors] };
|
|
57
|
+
}
|
|
58
|
+
const result = (0, caws_kernel_1.parseAndValidatePolicy)(source.value);
|
|
59
|
+
if (!(0, caws_kernel_1.isOk)(result)) {
|
|
60
|
+
return { warnings: [], errors: [...result.errors] };
|
|
61
|
+
}
|
|
62
|
+
const warnings = result.warnings ?? [];
|
|
63
|
+
return { policy: result.value, warnings: [...warnings], errors: [] };
|
|
64
|
+
}
|
|
65
|
+
//# sourceMappingURL=policy-store.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"policy-store.js","sourceRoot":"","sources":["../../src/store/policy-store.ts"],"names":[],"mappings":";AAAA,iBAAiB;AACjB,EAAE;AACF,8DAA8D;AAC9D,uEAAuE;AACvE,sEAAsE;AACtE,wEAAwE;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAYxE,gCAmBC;AA7BD,2CAA6B;AAC7B,2DAImC;AACnC,mCAAsC;AACtC,6CAA8C;AAG9C,SAAgB,UAAU,CAAC,OAAe;IACxC,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,aAAa,CAAC,CAAC;IACrD,MAAM,MAAM,GAAG,IAAA,2BAAc,EAAC,UAAU,CAAC,CAAC;IAC1C,IAAI,CAAC,IAAA,kBAAI,EAAC,MAAM,CAAC,EAAE,CAAC;QAClB,kEAAkE;QAClE,MAAM,OAAO,GAAG,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,mBAAW,CAAC,iBAAiB,CAAC,CAAC;QACpF,IAAI,OAAO,EAAE,CAAC;YACZ,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;QACtC,CAAC;QACD,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC;IACtD,CAAC;IAED,MAAM,MAAM,GAAG,IAAA,oCAAsB,EAAC,MAAM,CAAC,KAAK,CAAC,CAAC;IACpD,IAAI,CAAC,IAAA,kBAAI,EAAC,MAAM,CAAC,EAAE,CAAC;QAClB,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,EAAE,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC;IACtD,CAAC;IAED,MAAM,QAAQ,GAA0B,MAAM,CAAC,QAAQ,IAAI,EAAE,CAAC;IAC9D,OAAO,EAAE,MAAM,EAAE,MAAM,CAAC,KAAK,EAAE,QAAQ,EAAE,CAAC,GAAG,QAAQ,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;AACvE,CAAC"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { type Diagnostic, type Result } from '@paths.design/caws-kernel';
|
|
2
|
+
export interface RepoRoot {
|
|
3
|
+
/** Absolute path to the main repository root (parent of .git common dir). */
|
|
4
|
+
readonly repoRoot: string;
|
|
5
|
+
/** Absolute path to the .caws/ directory under the repo root. */
|
|
6
|
+
readonly cawsDir: string;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Pluggable git invoker. Tests stub this; production uses execFileSync.
|
|
10
|
+
*
|
|
11
|
+
* Returns the trimmed stdout on success, or throws on non-zero exit. The
|
|
12
|
+
* caller distinguishes "not a git repo" by inspecting the thrown error's
|
|
13
|
+
* stderr / status, which production execFileSync surfaces.
|
|
14
|
+
*/
|
|
15
|
+
export type GitRunner = (args: readonly string[], options: {
|
|
16
|
+
cwd: string;
|
|
17
|
+
}) => string;
|
|
18
|
+
export declare const defaultGitRunner: GitRunner;
|
|
19
|
+
export interface ResolveRepoRootOptions {
|
|
20
|
+
readonly git?: GitRunner;
|
|
21
|
+
/**
|
|
22
|
+
* If true, the .caws/ directory must already exist on disk. When false
|
|
23
|
+
* (default) the function only resolves where it WOULD be, leaving
|
|
24
|
+
* creation to a different layer (e.g., `caws init`).
|
|
25
|
+
*/
|
|
26
|
+
readonly requireCawsDir?: boolean;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Resolve the main-repo root from `cwd`, even when cwd is inside a linked
|
|
30
|
+
* worktree.
|
|
31
|
+
*
|
|
32
|
+
* Returns Err when:
|
|
33
|
+
* - cwd is not inside a git repository, OR
|
|
34
|
+
* - git invocation fails for another reason, OR
|
|
35
|
+
* - `requireCawsDir: true` and `.caws/` does not exist.
|
|
36
|
+
*
|
|
37
|
+
* Programmer errors (cwd not a string, git binary missing) throw.
|
|
38
|
+
*/
|
|
39
|
+
export declare function resolveRepoRoot(cwd: string, options?: ResolveRepoRootOptions): Result<RepoRoot>;
|
|
40
|
+
/** Construct a structured Diagnostic with the canonical store authority. */
|
|
41
|
+
export declare function storeDiagnostic(rule: string, message: string, extra?: {
|
|
42
|
+
subject?: string;
|
|
43
|
+
narrowRepair?: string;
|
|
44
|
+
data?: Record<string, unknown>;
|
|
45
|
+
}): Diagnostic;
|
|
46
|
+
//# sourceMappingURL=repo-root.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"repo-root.d.ts","sourceRoot":"","sources":["../../src/store/repo-root.ts"],"names":[],"mappings":"AAoBA,OAAO,EAIL,KAAK,UAAU,EACf,KAAK,MAAM,EACZ,MAAM,2BAA2B,CAAC;AAOnC,MAAM,WAAW,QAAQ;IACvB,6EAA6E;IAC7E,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,iEAAiE;IACjE,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;;GAMG;AACH,MAAM,MAAM,SAAS,GAAG,CACtB,IAAI,EAAE,SAAS,MAAM,EAAE,EACvB,OAAO,EAAE;IAAE,GAAG,EAAE,MAAM,CAAA;CAAE,KACrB,MAAM,CAAC;AAEZ,eAAO,MAAM,gBAAgB,EAAE,SAO9B,CAAC;AAMF,MAAM,WAAW,sBAAsB;IACrC,QAAQ,CAAC,GAAG,CAAC,EAAE,SAAS,CAAC;IACzB;;;;OAIG;IACH,QAAQ,CAAC,cAAc,CAAC,EAAE,OAAO,CAAC;CACnC;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,eAAe,CAC7B,GAAG,EAAE,MAAM,EACX,OAAO,GAAE,sBAA2B,GACnC,MAAM,CAAC,QAAQ,CAAC,CA6DlB;AAMD,4EAA4E;AAC5E,wBAAgB,eAAe,CAC7B,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,MAAM,EACf,KAAK,GAAE;IAAE,OAAO,CAAC,EAAE,MAAM,CAAC;IAAC,YAAY,CAAC,EAAE,MAAM,CAAC;IAAC,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;CAAO,GACtF,UAAU,CASZ"}
|