@manehorizons/cadence-core 1.1.1
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/LICENSE +21 -0
- package/README.md +5 -0
- package/bin/cadence.cjs +4 -0
- package/dist/build/record.d.ts +16 -0
- package/dist/build/record.d.ts.map +1 -0
- package/dist/build/record.js +33 -0
- package/dist/build/record.js.map +1 -0
- package/dist/checks/boundary.d.ts +35 -0
- package/dist/checks/boundary.d.ts.map +1 -0
- package/dist/checks/boundary.js +29 -0
- package/dist/checks/boundary.js.map +1 -0
- package/dist/checks/skill-audit.d.ts +29 -0
- package/dist/checks/skill-audit.d.ts.map +1 -0
- package/dist/checks/skill-audit.js +57 -0
- package/dist/checks/skill-audit.js.map +1 -0
- package/dist/classify/tier.d.ts +9 -0
- package/dist/classify/tier.d.ts.map +1 -0
- package/dist/classify/tier.js +15 -0
- package/dist/classify/tier.js.map +1 -0
- package/dist/cli/commands/assumption.d.ts +3 -0
- package/dist/cli/commands/assumption.d.ts.map +1 -0
- package/dist/cli/commands/assumption.js +313 -0
- package/dist/cli/commands/assumption.js.map +1 -0
- package/dist/cli/commands/block.d.ts +3 -0
- package/dist/cli/commands/block.d.ts.map +1 -0
- package/dist/cli/commands/block.js +23 -0
- package/dist/cli/commands/block.js.map +1 -0
- package/dist/cli/commands/build.d.ts +3 -0
- package/dist/cli/commands/build.d.ts.map +1 -0
- package/dist/cli/commands/build.js +89 -0
- package/dist/cli/commands/build.js.map +1 -0
- package/dist/cli/commands/config.d.ts +3 -0
- package/dist/cli/commands/config.d.ts.map +1 -0
- package/dist/cli/commands/config.js +91 -0
- package/dist/cli/commands/config.js.map +1 -0
- package/dist/cli/commands/context.d.ts +3 -0
- package/dist/cli/commands/context.d.ts.map +1 -0
- package/dist/cli/commands/context.js +31 -0
- package/dist/cli/commands/context.js.map +1 -0
- package/dist/cli/commands/decision.d.ts +3 -0
- package/dist/cli/commands/decision.d.ts.map +1 -0
- package/dist/cli/commands/decision.js +390 -0
- package/dist/cli/commands/decision.js.map +1 -0
- package/dist/cli/commands/done.d.ts +3 -0
- package/dist/cli/commands/done.d.ts.map +1 -0
- package/dist/cli/commands/done.js +23 -0
- package/dist/cli/commands/done.js.map +1 -0
- package/dist/cli/commands/draft-new.d.ts +4 -0
- package/dist/cli/commands/draft-new.d.ts.map +1 -0
- package/dist/cli/commands/draft-new.js +108 -0
- package/dist/cli/commands/draft-new.js.map +1 -0
- package/dist/cli/commands/draft.d.ts +4 -0
- package/dist/cli/commands/draft.d.ts.map +1 -0
- package/dist/cli/commands/draft.js +125 -0
- package/dist/cli/commands/draft.js.map +1 -0
- package/dist/cli/commands/hook.d.ts +3 -0
- package/dist/cli/commands/hook.d.ts.map +1 -0
- package/dist/cli/commands/hook.js +50 -0
- package/dist/cli/commands/hook.js.map +1 -0
- package/dist/cli/commands/init.d.ts +21 -0
- package/dist/cli/commands/init.d.ts.map +1 -0
- package/dist/cli/commands/init.js +255 -0
- package/dist/cli/commands/init.js.map +1 -0
- package/dist/cli/commands/inspect.d.ts +3 -0
- package/dist/cli/commands/inspect.d.ts.map +1 -0
- package/dist/cli/commands/inspect.js +24 -0
- package/dist/cli/commands/inspect.js.map +1 -0
- package/dist/cli/commands/intelligence.d.ts +3 -0
- package/dist/cli/commands/intelligence.d.ts.map +1 -0
- package/dist/cli/commands/intelligence.js +173 -0
- package/dist/cli/commands/intelligence.js.map +1 -0
- package/dist/cli/commands/milestone.d.ts +3 -0
- package/dist/cli/commands/milestone.d.ts.map +1 -0
- package/dist/cli/commands/milestone.js +119 -0
- package/dist/cli/commands/milestone.js.map +1 -0
- package/dist/cli/commands/needs-context.d.ts +3 -0
- package/dist/cli/commands/needs-context.d.ts.map +1 -0
- package/dist/cli/commands/needs-context.js +23 -0
- package/dist/cli/commands/needs-context.js.map +1 -0
- package/dist/cli/commands/progress.d.ts +3 -0
- package/dist/cli/commands/progress.d.ts.map +1 -0
- package/dist/cli/commands/progress.js +21 -0
- package/dist/cli/commands/progress.js.map +1 -0
- package/dist/cli/commands/recommend.d.ts +3 -0
- package/dist/cli/commands/recommend.d.ts.map +1 -0
- package/dist/cli/commands/recommend.js +24 -0
- package/dist/cli/commands/recommend.js.map +1 -0
- package/dist/cli/commands/recommendation.d.ts +3 -0
- package/dist/cli/commands/recommendation.d.ts.map +1 -0
- package/dist/cli/commands/recommendation.js +360 -0
- package/dist/cli/commands/recommendation.js.map +1 -0
- package/dist/cli/commands/settle.d.ts +3 -0
- package/dist/cli/commands/settle.d.ts.map +1 -0
- package/dist/cli/commands/settle.js +453 -0
- package/dist/cli/commands/settle.js.map +1 -0
- package/dist/cli/commands/spec.d.ts +10 -0
- package/dist/cli/commands/spec.d.ts.map +1 -0
- package/dist/cli/commands/spec.js +246 -0
- package/dist/cli/commands/spec.js.map +1 -0
- package/dist/cli/commands/status.d.ts +11 -0
- package/dist/cli/commands/status.d.ts.map +1 -0
- package/dist/cli/commands/status.js +211 -0
- package/dist/cli/commands/status.js.map +1 -0
- package/dist/cli/index.d.ts +3 -0
- package/dist/cli/index.d.ts.map +1 -0
- package/dist/cli/index.js +21 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/register.d.ts +3 -0
- package/dist/cli/register.d.ts.map +1 -0
- package/dist/cli/register.js +43 -0
- package/dist/cli/register.js.map +1 -0
- package/dist/coherence/check.d.ts +11 -0
- package/dist/coherence/check.d.ts.map +1 -0
- package/dist/coherence/check.js +34 -0
- package/dist/coherence/check.js.map +1 -0
- package/dist/config/loader.d.ts +4 -0
- package/dist/config/loader.d.ts.map +1 -0
- package/dist/config/loader.js +40 -0
- package/dist/config/loader.js.map +1 -0
- package/dist/errors.d.ts +23 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.js +31 -0
- package/dist/errors.js.map +1 -0
- package/dist/gates/approve.d.ts +20 -0
- package/dist/gates/approve.d.ts.map +1 -0
- package/dist/gates/approve.js +55 -0
- package/dist/gates/approve.js.map +1 -0
- package/dist/gates/build-context.d.ts +17 -0
- package/dist/gates/build-context.d.ts.map +1 -0
- package/dist/gates/build-context.js +81 -0
- package/dist/gates/build-context.js.map +1 -0
- package/dist/gates/build-test-must-pass.d.ts +12 -0
- package/dist/gates/build-test-must-pass.d.ts.map +1 -0
- package/dist/gates/build-test-must-pass.js +23 -0
- package/dist/gates/build-test-must-pass.js.map +1 -0
- package/dist/gates/build-types.d.ts +54 -0
- package/dist/gates/build-types.d.ts.map +1 -0
- package/dist/gates/build-types.js +2 -0
- package/dist/gates/build-types.js.map +1 -0
- package/dist/gates/code-review.d.ts +20 -0
- package/dist/gates/code-review.d.ts.map +1 -0
- package/dist/gates/code-review.js +137 -0
- package/dist/gates/code-review.js.map +1 -0
- package/dist/gates/coherence.d.ts +26 -0
- package/dist/gates/coherence.d.ts.map +1 -0
- package/dist/gates/coherence.js +59 -0
- package/dist/gates/coherence.js.map +1 -0
- package/dist/gates/coverage.d.ts +8 -0
- package/dist/gates/coverage.d.ts.map +1 -0
- package/dist/gates/coverage.js +26 -0
- package/dist/gates/coverage.js.map +1 -0
- package/dist/gates/deep-verify.d.ts +7 -0
- package/dist/gates/deep-verify.d.ts.map +1 -0
- package/dist/gates/deep-verify.js +77 -0
- package/dist/gates/deep-verify.js.map +1 -0
- package/dist/gates/draft-context.d.ts +20 -0
- package/dist/gates/draft-context.d.ts.map +1 -0
- package/dist/gates/draft-context.js +87 -0
- package/dist/gates/draft-context.js.map +1 -0
- package/dist/gates/draft-read.d.ts +10 -0
- package/dist/gates/draft-read.d.ts.map +1 -0
- package/dist/gates/draft-read.js +24 -0
- package/dist/gates/draft-read.js.map +1 -0
- package/dist/gates/draft-types.d.ts +75 -0
- package/dist/gates/draft-types.d.ts.map +1 -0
- package/dist/gates/draft-types.js +2 -0
- package/dist/gates/draft-types.js.map +1 -0
- package/dist/gates/engine.d.ts +21 -0
- package/dist/gates/engine.d.ts.map +1 -0
- package/dist/gates/engine.js +98 -0
- package/dist/gates/engine.js.map +1 -0
- package/dist/gates/interactive.d.ts +11 -0
- package/dist/gates/interactive.d.ts.map +1 -0
- package/dist/gates/interactive.js +55 -0
- package/dist/gates/interactive.js.map +1 -0
- package/dist/gates/per-task-verify.d.ts +12 -0
- package/dist/gates/per-task-verify.d.ts.map +1 -0
- package/dist/gates/per-task-verify.js +52 -0
- package/dist/gates/per-task-verify.js.map +1 -0
- package/dist/gates/plan-review.d.ts +13 -0
- package/dist/gates/plan-review.d.ts.map +1 -0
- package/dist/gates/plan-review.js +98 -0
- package/dist/gates/plan-review.js.map +1 -0
- package/dist/gates/registry.d.ts +53 -0
- package/dist/gates/registry.d.ts.map +1 -0
- package/dist/gates/registry.js +66 -0
- package/dist/gates/registry.js.map +1 -0
- package/dist/gates/security-audit.d.ts +11 -0
- package/dist/gates/security-audit.d.ts.map +1 -0
- package/dist/gates/security-audit.js +40 -0
- package/dist/gates/security-audit.js.map +1 -0
- package/dist/gates/structural-verifier.d.ts +8 -0
- package/dist/gates/structural-verifier.d.ts.map +1 -0
- package/dist/gates/structural-verifier.js +25 -0
- package/dist/gates/structural-verifier.js.map +1 -0
- package/dist/gates/types.d.ts +202 -0
- package/dist/gates/types.d.ts.map +1 -0
- package/dist/gates/types.js +12 -0
- package/dist/gates/types.js.map +1 -0
- package/dist/hooks/dispatcher.d.ts +8 -0
- package/dist/hooks/dispatcher.d.ts.map +1 -0
- package/dist/hooks/dispatcher.js +31 -0
- package/dist/hooks/dispatcher.js.map +1 -0
- package/dist/hooks/handlers.d.ts +21 -0
- package/dist/hooks/handlers.d.ts.map +1 -0
- package/dist/hooks/handlers.js +121 -0
- package/dist/hooks/handlers.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +2 -0
- package/dist/index.js.map +1 -0
- package/dist/init/claude-md-template.d.ts +34 -0
- package/dist/init/claude-md-template.d.ts.map +1 -0
- package/dist/init/claude-md-template.js +72 -0
- package/dist/init/claude-md-template.js.map +1 -0
- package/dist/intelligence/backend/cadence.d.ts +21 -0
- package/dist/intelligence/backend/cadence.d.ts.map +1 -0
- package/dist/intelligence/backend/cadence.js +127 -0
- package/dist/intelligence/backend/cadence.js.map +1 -0
- package/dist/intelligence/context.d.ts +11 -0
- package/dist/intelligence/context.d.ts.map +1 -0
- package/dist/intelligence/context.js +197 -0
- package/dist/intelligence/context.js.map +1 -0
- package/dist/intelligence/graph-decision.d.ts +9 -0
- package/dist/intelligence/graph-decision.d.ts.map +1 -0
- package/dist/intelligence/graph-decision.js +55 -0
- package/dist/intelligence/graph-decision.js.map +1 -0
- package/dist/intelligence/inspect.d.ts +9 -0
- package/dist/intelligence/inspect.d.ts.map +1 -0
- package/dist/intelligence/inspect.js +93 -0
- package/dist/intelligence/inspect.js.map +1 -0
- package/dist/intelligence/milestone.d.ts +40 -0
- package/dist/intelligence/milestone.d.ts.map +1 -0
- package/dist/intelligence/milestone.js +312 -0
- package/dist/intelligence/milestone.js.map +1 -0
- package/dist/intelligence/recommend.d.ts +20 -0
- package/dist/intelligence/recommend.d.ts.map +1 -0
- package/dist/intelligence/recommend.js +185 -0
- package/dist/intelligence/recommend.js.map +1 -0
- package/dist/intelligence/render-assumption-detail.d.ts +3 -0
- package/dist/intelligence/render-assumption-detail.d.ts.map +1 -0
- package/dist/intelligence/render-assumption-detail.js +16 -0
- package/dist/intelligence/render-assumption-detail.js.map +1 -0
- package/dist/intelligence/render-assumption.d.ts +3 -0
- package/dist/intelligence/render-assumption.d.ts.map +1 -0
- package/dist/intelligence/render-assumption.js +37 -0
- package/dist/intelligence/render-assumption.js.map +1 -0
- package/dist/intelligence/render-context.d.ts +3 -0
- package/dist/intelligence/render-context.d.ts.map +1 -0
- package/dist/intelligence/render-context.js +92 -0
- package/dist/intelligence/render-context.js.map +1 -0
- package/dist/intelligence/render-decision-detail.d.ts +3 -0
- package/dist/intelligence/render-decision-detail.d.ts.map +1 -0
- package/dist/intelligence/render-decision-detail.js +30 -0
- package/dist/intelligence/render-decision-detail.js.map +1 -0
- package/dist/intelligence/render-decision-graph.d.ts +3 -0
- package/dist/intelligence/render-decision-graph.d.ts.map +1 -0
- package/dist/intelligence/render-decision-graph.js +49 -0
- package/dist/intelligence/render-decision-graph.js.map +1 -0
- package/dist/intelligence/render-decision.d.ts +3 -0
- package/dist/intelligence/render-decision.d.ts.map +1 -0
- package/dist/intelligence/render-decision.js +45 -0
- package/dist/intelligence/render-decision.js.map +1 -0
- package/dist/intelligence/render-inspection.d.ts +3 -0
- package/dist/intelligence/render-inspection.d.ts.map +1 -0
- package/dist/intelligence/render-inspection.js +69 -0
- package/dist/intelligence/render-inspection.js.map +1 -0
- package/dist/intelligence/render-intelligence-audit.d.ts +5 -0
- package/dist/intelligence/render-intelligence-audit.d.ts.map +1 -0
- package/dist/intelligence/render-intelligence-audit.js +93 -0
- package/dist/intelligence/render-intelligence-audit.js.map +1 -0
- package/dist/intelligence/render-intelligence-stats.d.ts +6 -0
- package/dist/intelligence/render-intelligence-stats.d.ts.map +1 -0
- package/dist/intelligence/render-intelligence-stats.js +76 -0
- package/dist/intelligence/render-intelligence-stats.js.map +1 -0
- package/dist/intelligence/render-milestone.d.ts +3 -0
- package/dist/intelligence/render-milestone.d.ts.map +1 -0
- package/dist/intelligence/render-milestone.js +80 -0
- package/dist/intelligence/render-milestone.js.map +1 -0
- package/dist/intelligence/render-recommend.d.ts +3 -0
- package/dist/intelligence/render-recommend.d.ts.map +1 -0
- package/dist/intelligence/render-recommend.js +62 -0
- package/dist/intelligence/render-recommend.js.map +1 -0
- package/dist/intelligence/render-recommendation-detail.d.ts +7 -0
- package/dist/intelligence/render-recommendation-detail.d.ts.map +1 -0
- package/dist/intelligence/render-recommendation-detail.js +93 -0
- package/dist/intelligence/render-recommendation-detail.js.map +1 -0
- package/dist/intelligence/render.d.ts +3 -0
- package/dist/intelligence/render.d.ts.map +1 -0
- package/dist/intelligence/render.js +57 -0
- package/dist/intelligence/render.js.map +1 -0
- package/dist/intelligence/scan.d.ts +3 -0
- package/dist/intelligence/scan.d.ts.map +1 -0
- package/dist/intelligence/scan.js +103 -0
- package/dist/intelligence/scan.js.map +1 -0
- package/dist/intelligence/store.d.ts +143 -0
- package/dist/intelligence/store.d.ts.map +1 -0
- package/dist/intelligence/store.js +701 -0
- package/dist/intelligence/store.js.map +1 -0
- package/dist/notify/code-review.d.ts +34 -0
- package/dist/notify/code-review.d.ts.map +1 -0
- package/dist/notify/code-review.js +56 -0
- package/dist/notify/code-review.js.map +1 -0
- package/dist/notify/collect.d.ts +31 -0
- package/dist/notify/collect.d.ts.map +1 -0
- package/dist/notify/collect.js +127 -0
- package/dist/notify/collect.js.map +1 -0
- package/dist/notify/emit-unconverged.d.ts +26 -0
- package/dist/notify/emit-unconverged.d.ts.map +1 -0
- package/dist/notify/emit-unconverged.js +31 -0
- package/dist/notify/emit-unconverged.js.map +1 -0
- package/dist/notify/factory.d.ts +12 -0
- package/dist/notify/factory.d.ts.map +1 -0
- package/dist/notify/factory.js +29 -0
- package/dist/notify/factory.js.map +1 -0
- package/dist/notify/file.d.ts +13 -0
- package/dist/notify/file.d.ts.map +1 -0
- package/dist/notify/file.js +21 -0
- package/dist/notify/file.js.map +1 -0
- package/dist/notify/loop-violation.d.ts +10 -0
- package/dist/notify/loop-violation.d.ts.map +1 -0
- package/dist/notify/loop-violation.js +46 -0
- package/dist/notify/loop-violation.js.map +1 -0
- package/dist/notify/notifier.d.ts +13 -0
- package/dist/notify/notifier.d.ts.map +1 -0
- package/dist/notify/notifier.js +2 -0
- package/dist/notify/notifier.js.map +1 -0
- package/dist/notify/null.d.ts +11 -0
- package/dist/notify/null.d.ts.map +1 -0
- package/dist/notify/null.js +11 -0
- package/dist/notify/null.js.map +1 -0
- package/dist/notify/plan-review.d.ts +20 -0
- package/dist/notify/plan-review.d.ts.map +1 -0
- package/dist/notify/plan-review.js +15 -0
- package/dist/notify/plan-review.js.map +1 -0
- package/dist/notify/skill-audit.d.ts +18 -0
- package/dist/notify/skill-audit.d.ts.map +1 -0
- package/dist/notify/skill-audit.js +33 -0
- package/dist/notify/skill-audit.js.map +1 -0
- package/dist/notify/spec-review.d.ts +20 -0
- package/dist/notify/spec-review.d.ts.map +1 -0
- package/dist/notify/spec-review.js +15 -0
- package/dist/notify/spec-review.js.map +1 -0
- package/dist/notify/stderr.d.ts +17 -0
- package/dist/notify/stderr.d.ts.map +1 -0
- package/dist/notify/stderr.js +17 -0
- package/dist/notify/stderr.js.map +1 -0
- package/dist/notify/webhook.d.ts +33 -0
- package/dist/notify/webhook.d.ts.map +1 -0
- package/dist/notify/webhook.js +55 -0
- package/dist/notify/webhook.js.map +1 -0
- package/dist/parse/draft-parser.d.ts +3 -0
- package/dist/parse/draft-parser.d.ts.map +1 -0
- package/dist/parse/draft-parser.js +99 -0
- package/dist/parse/draft-parser.js.map +1 -0
- package/dist/parse/draft-scaffold.d.ts +14 -0
- package/dist/parse/draft-scaffold.d.ts.map +1 -0
- package/dist/parse/draft-scaffold.js +31 -0
- package/dist/parse/draft-scaffold.js.map +1 -0
- package/dist/parse/spec-parser.d.ts +3 -0
- package/dist/parse/spec-parser.d.ts.map +1 -0
- package/dist/parse/spec-parser.js +68 -0
- package/dist/parse/spec-parser.js.map +1 -0
- package/dist/parse/summary-writer.d.ts +3 -0
- package/dist/parse/summary-writer.d.ts.map +1 -0
- package/dist/parse/summary-writer.js +41 -0
- package/dist/parse/summary-writer.js.map +1 -0
- package/dist/progress.d.ts +7 -0
- package/dist/progress.d.ts.map +1 -0
- package/dist/progress.js +37 -0
- package/dist/progress.js.map +1 -0
- package/dist/render/state-md.d.ts +3 -0
- package/dist/render/state-md.d.ts.map +1 -0
- package/dist/render/state-md.js +33 -0
- package/dist/render/state-md.js.map +1 -0
- package/dist/state/atomic-write.d.ts +3 -0
- package/dist/state/atomic-write.d.ts.map +1 -0
- package/dist/state/atomic-write.js +52 -0
- package/dist/state/atomic-write.js.map +1 -0
- package/dist/state/backend.d.ts +13 -0
- package/dist/state/backend.d.ts.map +1 -0
- package/dist/state/backend.js +2 -0
- package/dist/state/backend.js.map +1 -0
- package/dist/state/simple.d.ts +18 -0
- package/dist/state/simple.d.ts.map +1 -0
- package/dist/state/simple.js +67 -0
- package/dist/state/simple.js.map +1 -0
- package/dist/status.d.ts +47 -0
- package/dist/status.d.ts.map +1 -0
- package/dist/status.js +209 -0
- package/dist/status.js.map +1 -0
- package/dist/verify/anthropic-verifier.d.ts +28 -0
- package/dist/verify/anthropic-verifier.d.ts.map +1 -0
- package/dist/verify/anthropic-verifier.js +109 -0
- package/dist/verify/anthropic-verifier.js.map +1 -0
- package/dist/verify/code-review-factory.d.ts +103 -0
- package/dist/verify/code-review-factory.d.ts.map +1 -0
- package/dist/verify/code-review-factory.js +11 -0
- package/dist/verify/code-review-factory.js.map +1 -0
- package/dist/verify/code-review.d.ts +65 -0
- package/dist/verify/code-review.d.ts.map +1 -0
- package/dist/verify/code-review.js +189 -0
- package/dist/verify/code-review.js.map +1 -0
- package/dist/verify/converge.d.ts +14 -0
- package/dist/verify/converge.d.ts.map +1 -0
- package/dist/verify/converge.js +17 -0
- package/dist/verify/converge.js.map +1 -0
- package/dist/verify/coverage.d.ts +31 -0
- package/dist/verify/coverage.d.ts.map +1 -0
- package/dist/verify/coverage.js +125 -0
- package/dist/verify/coverage.js.map +1 -0
- package/dist/verify/factory.d.ts +107 -0
- package/dist/verify/factory.d.ts.map +1 -0
- package/dist/verify/factory.js +17 -0
- package/dist/verify/factory.js.map +1 -0
- package/dist/verify/interactive.d.ts +22 -0
- package/dist/verify/interactive.d.ts.map +1 -0
- package/dist/verify/interactive.js +61 -0
- package/dist/verify/interactive.js.map +1 -0
- package/dist/verify/local-client.d.ts +13 -0
- package/dist/verify/local-client.d.ts.map +1 -0
- package/dist/verify/local-client.js +73 -0
- package/dist/verify/local-client.js.map +1 -0
- package/dist/verify/mock-verifier.d.ts +16 -0
- package/dist/verify/mock-verifier.d.ts.map +1 -0
- package/dist/verify/mock-verifier.js +30 -0
- package/dist/verify/mock-verifier.js.map +1 -0
- package/dist/verify/per-task-factory.d.ts +103 -0
- package/dist/verify/per-task-factory.d.ts.map +1 -0
- package/dist/verify/per-task-factory.js +11 -0
- package/dist/verify/per-task-factory.js.map +1 -0
- package/dist/verify/per-task.d.ts +69 -0
- package/dist/verify/per-task.d.ts.map +1 -0
- package/dist/verify/per-task.js +154 -0
- package/dist/verify/per-task.js.map +1 -0
- package/dist/verify/plan-review-factory.d.ts +103 -0
- package/dist/verify/plan-review-factory.d.ts.map +1 -0
- package/dist/verify/plan-review-factory.js +11 -0
- package/dist/verify/plan-review-factory.js.map +1 -0
- package/dist/verify/plan-review.d.ts +67 -0
- package/dist/verify/plan-review.d.ts.map +1 -0
- package/dist/verify/plan-review.js +196 -0
- package/dist/verify/plan-review.js.map +1 -0
- package/dist/verify/prompter.d.ts +40 -0
- package/dist/verify/prompter.d.ts.map +1 -0
- package/dist/verify/prompter.js +48 -0
- package/dist/verify/prompter.js.map +1 -0
- package/dist/verify/security-audit-factory.d.ts +103 -0
- package/dist/verify/security-audit-factory.d.ts.map +1 -0
- package/dist/verify/security-audit-factory.js +11 -0
- package/dist/verify/security-audit-factory.js.map +1 -0
- package/dist/verify/security-audit.d.ts +63 -0
- package/dist/verify/security-audit.d.ts.map +1 -0
- package/dist/verify/security-audit.js +196 -0
- package/dist/verify/security-audit.js.map +1 -0
- package/dist/verify/skill-match.d.ts +10 -0
- package/dist/verify/skill-match.d.ts.map +1 -0
- package/dist/verify/skill-match.js +15 -0
- package/dist/verify/skill-match.js.map +1 -0
- package/dist/verify/spec-review-factory.d.ts +103 -0
- package/dist/verify/spec-review-factory.d.ts.map +1 -0
- package/dist/verify/spec-review-factory.js +11 -0
- package/dist/verify/spec-review-factory.js.map +1 -0
- package/dist/verify/spec-review.d.ts +63 -0
- package/dist/verify/spec-review.d.ts.map +1 -0
- package/dist/verify/spec-review.js +182 -0
- package/dist/verify/spec-review.js.map +1 -0
- package/dist/verify/verifier-factory.d.ts +45 -0
- package/dist/verify/verifier-factory.d.ts.map +1 -0
- package/dist/verify/verifier-factory.js +38 -0
- package/dist/verify/verifier-factory.js.map +1 -0
- package/dist/verify/verifier.d.ts +63 -0
- package/dist/verify/verifier.d.ts.map +1 -0
- package/dist/verify/verifier.js +32 -0
- package/dist/verify/verifier.js.map +1 -0
- package/package.json +62 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Thomas Powers
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
package/bin/cadence.cjs
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { TaskStatus } from '@manehorizons/cadence-types';
|
|
2
|
+
export type RecordableStatus = Exclude<TaskStatus, 'PENDING' | 'IN_PROGRESS'>;
|
|
3
|
+
/**
|
|
4
|
+
* Phase 24.2 — per-task verifier verdict attached to a task row when
|
|
5
|
+
* the `'per-task-verify'` gate fires. `bypassed` is true when the user
|
|
6
|
+
* passed `--allow-per-task-failure` to record a `refuse` verdict anyway.
|
|
7
|
+
*/
|
|
8
|
+
export interface PerTaskVerifyRecord {
|
|
9
|
+
verdict: 'pass' | 'concerns' | 'refuse';
|
|
10
|
+
reason: string;
|
|
11
|
+
provider: string;
|
|
12
|
+
model?: string;
|
|
13
|
+
bypassed?: boolean;
|
|
14
|
+
}
|
|
15
|
+
export declare function recordTaskOutcome(cwd: string, taskId: string, status: RecordableStatus, notes: string, perTaskVerify?: PerTaskVerifyRecord): Promise<void>;
|
|
16
|
+
//# sourceMappingURL=record.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"record.d.ts","sourceRoot":"","sources":["../../src/build/record.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,6BAA6B,CAAC;AAK9D,MAAM,MAAM,gBAAgB,GAAG,OAAO,CAAC,UAAU,EAAE,SAAS,GAAG,aAAa,CAAC,CAAC;AAE9E;;;;GAIG;AACH,MAAM,WAAW,mBAAmB;IAClC,OAAO,EAAE,MAAM,GAAG,UAAU,GAAG,QAAQ,CAAC;IACxC,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAgBD,wBAAsB,iBAAiB,CACrC,GAAG,EAAE,MAAM,EACX,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,gBAAgB,EACxB,KAAK,EAAE,MAAM,EACb,aAAa,CAAC,EAAE,mBAAmB,GAClC,OAAO,CAAC,IAAI,CAAC,CAgCf"}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { join } from 'node:path';
|
|
2
|
+
import { readFile } from 'node:fs/promises';
|
|
3
|
+
import { existsSync } from 'node:fs';
|
|
4
|
+
import { SimpleStateBackend } from '../state/simple.js';
|
|
5
|
+
import { atomicWriteJSON } from '../state/atomic-write.js';
|
|
6
|
+
import { LoopViolationError } from '../errors.js';
|
|
7
|
+
export async function recordTaskOutcome(cwd, taskId, status, notes, perTaskVerify) {
|
|
8
|
+
const backend = new SimpleStateBackend(cwd);
|
|
9
|
+
const state = await backend.readState();
|
|
10
|
+
if (state.loopPosition !== 'BUILD' || !state.activeDraft || !state.activePhase) {
|
|
11
|
+
throw new LoopViolationError('task outcome can only be recorded while loopPosition=BUILD with an active draft', { expected: 'BUILD', actual: state.loopPosition });
|
|
12
|
+
}
|
|
13
|
+
const progPath = join(cwd, '.cadence/phases', state.activePhase, `${state.activeDraft}-PROGRESS.json`);
|
|
14
|
+
let progress;
|
|
15
|
+
if (existsSync(progPath)) {
|
|
16
|
+
progress = JSON.parse(await readFile(progPath, 'utf8'));
|
|
17
|
+
}
|
|
18
|
+
else {
|
|
19
|
+
progress = { draftId: state.activeDraft, tasks: {} };
|
|
20
|
+
}
|
|
21
|
+
progress.tasks[taskId] = {
|
|
22
|
+
status,
|
|
23
|
+
notes,
|
|
24
|
+
touchedFiles: state.activeTask?.touchedFiles ?? [],
|
|
25
|
+
updatedAt: new Date().toISOString(),
|
|
26
|
+
...(perTaskVerify ? { perTaskVerify } : {}),
|
|
27
|
+
};
|
|
28
|
+
await atomicWriteJSON(progPath, progress);
|
|
29
|
+
state.activeTask = { id: taskId, status, touchedFiles: [] };
|
|
30
|
+
// Phase 41.1 — commit() also refreshes STATE.md (was stale after build task).
|
|
31
|
+
await backend.commit(state);
|
|
32
|
+
}
|
|
33
|
+
//# sourceMappingURL=record.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"record.js","sourceRoot":"","sources":["../../src/build/record.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAErC,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AACxD,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAC3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,cAAc,CAAC;AA+BlD,MAAM,CAAC,KAAK,UAAU,iBAAiB,CACrC,GAAW,EACX,MAAc,EACd,MAAwB,EACxB,KAAa,EACb,aAAmC;IAEnC,MAAM,OAAO,GAAG,IAAI,kBAAkB,CAAC,GAAG,CAAC,CAAC;IAC5C,MAAM,KAAK,GAAG,MAAM,OAAO,CAAC,SAAS,EAAE,CAAC;IACxC,IAAI,KAAK,CAAC,YAAY,KAAK,OAAO,IAAI,CAAC,KAAK,CAAC,WAAW,IAAI,CAAC,KAAK,CAAC,WAAW,EAAE,CAAC;QAC/E,MAAM,IAAI,kBAAkB,CAC1B,iFAAiF,EACjF,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,KAAK,CAAC,YAAY,EAAE,CAClD,CAAC;IACJ,CAAC;IACD,MAAM,QAAQ,GAAG,IAAI,CACnB,GAAG,EACH,iBAAiB,EACjB,KAAK,CAAC,WAAW,EACjB,GAAG,KAAK,CAAC,WAAW,gBAAgB,CACrC,CAAC;IACF,IAAI,QAAsB,CAAC;IAC3B,IAAI,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;QACzB,QAAQ,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC,CAAiB,CAAC;IAC1E,CAAC;SAAM,CAAC;QACN,QAAQ,GAAG,EAAE,OAAO,EAAE,KAAK,CAAC,WAAW,EAAE,KAAK,EAAE,EAAE,EAAE,CAAC;IACvD,CAAC;IACD,QAAQ,CAAC,KAAK,CAAC,MAAM,CAAC,GAAG;QACvB,MAAM;QACN,KAAK;QACL,YAAY,EAAE,KAAK,CAAC,UAAU,EAAE,YAAY,IAAI,EAAE;QAClD,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;QACnC,GAAG,CAAC,aAAa,CAAC,CAAC,CAAC,EAAE,aAAa,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC5C,CAAC;IACF,MAAM,eAAe,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;IAC1C,KAAK,CAAC,UAAU,GAAG,EAAE,EAAE,EAAE,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,EAAE,EAAE,CAAC;IAC5D,8EAA8E;IAC9E,MAAM,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;AAC9B,CAAC"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import type { AnomalyEvent } from '@manehorizons/cadence-types';
|
|
2
|
+
/** The single line both emission points use for a stray file. */
|
|
3
|
+
export declare const boundaryMessage: (file: string) => string;
|
|
4
|
+
export interface BoundaryCheckInput {
|
|
5
|
+
/** The allow-set: every file declared across all task `files:` lists. */
|
|
6
|
+
declaredFiles: Iterable<string>;
|
|
7
|
+
/**
|
|
8
|
+
* Candidate files to test against the boundary. Iterated as-given — the
|
|
9
|
+
* caller owns dedup/order: the PreToolEdit hook passes raw `ctx.raw.files`
|
|
10
|
+
* (keeps order + dups); settle passes a deduped `Set` of touched files.
|
|
11
|
+
*/
|
|
12
|
+
touchedFiles: Iterable<string>;
|
|
13
|
+
/**
|
|
14
|
+
* Stamps each event's `ts`. The hook precomputes one ISO string and returns
|
|
15
|
+
* it for every event; settle stamps per-event from its injectable clock.
|
|
16
|
+
*/
|
|
17
|
+
stamp: () => string;
|
|
18
|
+
/**
|
|
19
|
+
* Merged into each event's `context` AFTER the `file` key (e.g. the hook's
|
|
20
|
+
* `{ source: 'hook.preToolEdit' }`; settle supplies none).
|
|
21
|
+
*/
|
|
22
|
+
extraContext?: Record<string, unknown>;
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Phase 43.1 — the single home for files-outside-boundary detection. One rule
|
|
26
|
+
* ("a touched file not in the union of task `files:` is an outsider"), two
|
|
27
|
+
* emission points: the PreToolEdit hook (`hooks/handlers.ts`) and settle's
|
|
28
|
+
* `collectAnomalies` (`notify/collect.ts`). Pure — no I/O. Each outsider yields
|
|
29
|
+
* one `warn` `files-outside-boundary` event; emission (gate membership, notify,
|
|
30
|
+
* stderr-degrade) stays at each call site. NOT a `Gate` enum member — it is a
|
|
31
|
+
* hook-time + settle-time anomaly check, so it lives in `checks/` alongside
|
|
32
|
+
* skill-audit (39.6), OUTSIDE the Phase 44.1 registry.
|
|
33
|
+
*/
|
|
34
|
+
export declare function runBoundaryCheck(input: BoundaryCheckInput): AnomalyEvent[];
|
|
35
|
+
//# sourceMappingURL=boundary.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"boundary.d.ts","sourceRoot":"","sources":["../../src/checks/boundary.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAEhE,iEAAiE;AACjE,eAAO,MAAM,eAAe,GAAI,MAAM,MAAM,KAAG,MACU,CAAC;AAE1D,MAAM,WAAW,kBAAkB;IACjC,yEAAyE;IACzE,aAAa,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAC;IAChC;;;;OAIG;IACH,YAAY,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAC;IAC/B;;;OAGG;IACH,KAAK,EAAE,MAAM,MAAM,CAAC;IACpB;;;OAGG;IACH,YAAY,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACxC;AAED;;;;;;;;;GASG;AACH,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,kBAAkB,GAAG,YAAY,EAAE,CAc1E"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/** The single line both emission points use for a stray file. */
|
|
2
|
+
export const boundaryMessage = (file) => `${file} touched but not declared in any task's files:`;
|
|
3
|
+
/**
|
|
4
|
+
* Phase 43.1 — the single home for files-outside-boundary detection. One rule
|
|
5
|
+
* ("a touched file not in the union of task `files:` is an outsider"), two
|
|
6
|
+
* emission points: the PreToolEdit hook (`hooks/handlers.ts`) and settle's
|
|
7
|
+
* `collectAnomalies` (`notify/collect.ts`). Pure — no I/O. Each outsider yields
|
|
8
|
+
* one `warn` `files-outside-boundary` event; emission (gate membership, notify,
|
|
9
|
+
* stderr-degrade) stays at each call site. NOT a `Gate` enum member — it is a
|
|
10
|
+
* hook-time + settle-time anomaly check, so it lives in `checks/` alongside
|
|
11
|
+
* skill-audit (39.6), OUTSIDE the Phase 44.1 registry.
|
|
12
|
+
*/
|
|
13
|
+
export function runBoundaryCheck(input) {
|
|
14
|
+
const declared = new Set(input.declaredFiles);
|
|
15
|
+
const events = [];
|
|
16
|
+
for (const file of input.touchedFiles) {
|
|
17
|
+
if (declared.has(file))
|
|
18
|
+
continue;
|
|
19
|
+
events.push({
|
|
20
|
+
type: 'files-outside-boundary',
|
|
21
|
+
severity: 'warn',
|
|
22
|
+
message: boundaryMessage(file),
|
|
23
|
+
context: { file, ...input.extraContext },
|
|
24
|
+
ts: input.stamp(),
|
|
25
|
+
});
|
|
26
|
+
}
|
|
27
|
+
return events;
|
|
28
|
+
}
|
|
29
|
+
//# sourceMappingURL=boundary.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"boundary.js","sourceRoot":"","sources":["../../src/checks/boundary.ts"],"names":[],"mappings":"AAEA,iEAAiE;AACjE,MAAM,CAAC,MAAM,eAAe,GAAG,CAAC,IAAY,EAAU,EAAE,CACtD,GAAG,IAAI,gDAAgD,CAAC;AAuB1D;;;;;;;;;GASG;AACH,MAAM,UAAU,gBAAgB,CAAC,KAAyB;IACxD,MAAM,QAAQ,GAAG,IAAI,GAAG,CAAC,KAAK,CAAC,aAAa,CAAC,CAAC;IAC9C,MAAM,MAAM,GAAmB,EAAE,CAAC;IAClC,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,YAAY,EAAE,CAAC;QACtC,IAAI,QAAQ,CAAC,GAAG,CAAC,IAAI,CAAC;YAAE,SAAS;QACjC,MAAM,CAAC,IAAI,CAAC;YACV,IAAI,EAAE,wBAAwB;YAC9B,QAAQ,EAAE,MAAM;YAChB,OAAO,EAAE,eAAe,CAAC,IAAI,CAAC;YAC9B,OAAO,EAAE,EAAE,IAAI,EAAE,GAAG,KAAK,CAAC,YAAY,EAAE;YACxC,EAAE,EAAE,KAAK,CAAC,KAAK,EAAE;SAClB,CAAC,CAAC;IACL,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import type { SettleContext } from '../gates/types.js';
|
|
2
|
+
/**
|
|
3
|
+
* Result of the required-skill enforcement check. NOT a `GateResult`: it carries
|
|
4
|
+
* `effectiveRequired` so the settle adapter can record it on
|
|
5
|
+
* `state.skillAudit.required` (outside the `summaryPatch` contract), which is why
|
|
6
|
+
* this check is intentionally not a `GateImpl`.
|
|
7
|
+
*/
|
|
8
|
+
export interface SkillAuditResult {
|
|
9
|
+
readonly outcome: 'pass' | 'refuse';
|
|
10
|
+
/** config.skillAudit.required ∪ DRAFT requiredSkills, deduped, order-preserved.
|
|
11
|
+
* settle records it on state.skillAudit.required on every non-refuse path. */
|
|
12
|
+
readonly effectiveRequired: string[];
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Required-skill enforcement check (Phase 34.1 — ROADMAP 23.4). Extracted from
|
|
16
|
+
* settle.ts verbatim (Phase 39.6). NOT a `Gate` enum member — declaring required
|
|
17
|
+
* skills IS the opt-in, so it is an anomaly check, not a profile×tier gate. Lives
|
|
18
|
+
* in `checks/` and is dispatched EXPLICITLY by settle, OUTSIDE the Phase 44.1
|
|
19
|
+
* registry. It reuses `SettleContext` and reaches the notifier only through
|
|
20
|
+
* `ctx.emit.skillAuditMiss`.
|
|
21
|
+
*
|
|
22
|
+
* `config` is `… | null` (null when loadConfig failed). Deliberate null-config
|
|
23
|
+
* behavior: still compute + return the effective required set (so SUMMARY stays
|
|
24
|
+
* truthful) but SKIP enforcement — cannot read telemetry reliably; never
|
|
25
|
+
* false-refuse on a degraded-config path. The `skill-audit-miss` anomaly is
|
|
26
|
+
* UNCONDITIONAL (not under the `anomaly-notify` guard).
|
|
27
|
+
*/
|
|
28
|
+
export declare const runSkillAuditCheck: (ctx: SettleContext) => Promise<SkillAuditResult>;
|
|
29
|
+
//# sourceMappingURL=skill-audit.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"skill-audit.d.ts","sourceRoot":"","sources":["../../src/checks/skill-audit.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAGvD;;;;;GAKG;AACH,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,QAAQ,CAAC;IACpC;mFAC+E;IAC/E,QAAQ,CAAC,iBAAiB,EAAE,MAAM,EAAE,CAAC;CACtC;AAED;;;;;;;;;;;;;GAaG;AACH,eAAO,MAAM,kBAAkB,GAC7B,KAAK,aAAa,KACjB,OAAO,CAAC,gBAAgB,CA2C1B,CAAC"}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { missingSkills } from '../verify/skill-match.js';
|
|
2
|
+
/**
|
|
3
|
+
* Required-skill enforcement check (Phase 34.1 — ROADMAP 23.4). Extracted from
|
|
4
|
+
* settle.ts verbatim (Phase 39.6). NOT a `Gate` enum member — declaring required
|
|
5
|
+
* skills IS the opt-in, so it is an anomaly check, not a profile×tier gate. Lives
|
|
6
|
+
* in `checks/` and is dispatched EXPLICITLY by settle, OUTSIDE the Phase 44.1
|
|
7
|
+
* registry. It reuses `SettleContext` and reaches the notifier only through
|
|
8
|
+
* `ctx.emit.skillAuditMiss`.
|
|
9
|
+
*
|
|
10
|
+
* `config` is `… | null` (null when loadConfig failed). Deliberate null-config
|
|
11
|
+
* behavior: still compute + return the effective required set (so SUMMARY stays
|
|
12
|
+
* truthful) but SKIP enforcement — cannot read telemetry reliably; never
|
|
13
|
+
* false-refuse on a degraded-config path. The `skill-audit-miss` anomaly is
|
|
14
|
+
* UNCONDITIONAL (not under the `anomaly-notify` guard).
|
|
15
|
+
*/
|
|
16
|
+
export const runSkillAuditCheck = async (ctx) => {
|
|
17
|
+
const config = ctx.config;
|
|
18
|
+
const effectiveRequired = [
|
|
19
|
+
...new Set([
|
|
20
|
+
...(config?.skillAudit?.required ?? []),
|
|
21
|
+
...(ctx.draft.requiredSkills ?? []),
|
|
22
|
+
]),
|
|
23
|
+
];
|
|
24
|
+
if (effectiveRequired.length > 0 && config) {
|
|
25
|
+
const invoked = ctx.state.skillAudit.invoked;
|
|
26
|
+
if (!config.telemetry.skillInvocations) {
|
|
27
|
+
await ctx.emit.skillAuditMiss({
|
|
28
|
+
required: effectiveRequired,
|
|
29
|
+
invoked,
|
|
30
|
+
missing: effectiveRequired,
|
|
31
|
+
severity: 'warn',
|
|
32
|
+
unenforceable: true,
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
else {
|
|
36
|
+
const missing = missingSkills(effectiveRequired, invoked);
|
|
37
|
+
if (missing.length > 0) {
|
|
38
|
+
const bypass = ctx.opts.allowSkillAuditMiss === true;
|
|
39
|
+
await ctx.emit.skillAuditMiss({
|
|
40
|
+
required: effectiveRequired,
|
|
41
|
+
invoked,
|
|
42
|
+
missing,
|
|
43
|
+
severity: bypass ? 'warn' : 'error',
|
|
44
|
+
...(bypass ? { bypassed: true } : {}),
|
|
45
|
+
});
|
|
46
|
+
if (!bypass) {
|
|
47
|
+
ctx.io.err(`settle run refused: required skill(s) not invoked: ${missing.join(', ')}. ` +
|
|
48
|
+
`Invoke them, or pass --allow-skill-audit-miss to override.\n`);
|
|
49
|
+
return { outcome: 'refuse', effectiveRequired };
|
|
50
|
+
}
|
|
51
|
+
ctx.io.err(`skill-audit: --allow-skill-audit-miss set; proceeding past ${missing.length} missing skill(s).\n`);
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
return { outcome: 'pass', effectiveRequired };
|
|
56
|
+
};
|
|
57
|
+
//# sourceMappingURL=skill-audit.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"skill-audit.js","sourceRoot":"","sources":["../../src/checks/skill-audit.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAezD;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,KAAK,EACrC,GAAkB,EACS,EAAE;IAC7B,MAAM,MAAM,GAAG,GAAG,CAAC,MAAM,CAAC;IAC1B,MAAM,iBAAiB,GAAG;QACxB,GAAG,IAAI,GAAG,CAAC;YACT,GAAG,CAAC,MAAM,EAAE,UAAU,EAAE,QAAQ,IAAI,EAAE,CAAC;YACvC,GAAG,CAAC,GAAG,CAAC,KAAK,CAAC,cAAc,IAAI,EAAE,CAAC;SACpC,CAAC;KACH,CAAC;IACF,IAAI,iBAAiB,CAAC,MAAM,GAAG,CAAC,IAAI,MAAM,EAAE,CAAC;QAC3C,MAAM,OAAO,GAAG,GAAG,CAAC,KAAK,CAAC,UAAU,CAAC,OAAO,CAAC;QAC7C,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,gBAAgB,EAAE,CAAC;YACvC,MAAM,GAAG,CAAC,IAAI,CAAC,cAAc,CAAC;gBAC5B,QAAQ,EAAE,iBAAiB;gBAC3B,OAAO;gBACP,OAAO,EAAE,iBAAiB;gBAC1B,QAAQ,EAAE,MAAM;gBAChB,aAAa,EAAE,IAAI;aACpB,CAAC,CAAC;QACL,CAAC;aAAM,CAAC;YACN,MAAM,OAAO,GAAG,aAAa,CAAC,iBAAiB,EAAE,OAAO,CAAC,CAAC;YAC1D,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBACvB,MAAM,MAAM,GAAG,GAAG,CAAC,IAAI,CAAC,mBAAmB,KAAK,IAAI,CAAC;gBACrD,MAAM,GAAG,CAAC,IAAI,CAAC,cAAc,CAAC;oBAC5B,QAAQ,EAAE,iBAAiB;oBAC3B,OAAO;oBACP,OAAO;oBACP,QAAQ,EAAE,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,OAAO;oBACnC,GAAG,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;iBACtC,CAAC,CAAC;gBACH,IAAI,CAAC,MAAM,EAAE,CAAC;oBACZ,GAAG,CAAC,EAAE,CAAC,GAAG,CACR,sDAAsD,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI;wBAC1E,8DAA8D,CACjE,CAAC;oBACF,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,iBAAiB,EAAE,CAAC;gBAClD,CAAC;gBACD,GAAG,CAAC,EAAE,CAAC,GAAG,CACR,8DAA8D,OAAO,CAAC,MAAM,sBAAsB,CACnG,CAAC;YACJ,CAAC;QACH,CAAC;IACH,CAAC;IACD,OAAO,EAAE,OAAO,EAAE,MAAM,EAAE,iBAAiB,EAAE,CAAC;AAChD,CAAC,CAAC"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { Tier, CadenceConfig } from '@manehorizons/cadence-types';
|
|
2
|
+
export interface DraftSignals {
|
|
3
|
+
tasks: {
|
|
4
|
+
files: string[];
|
|
5
|
+
}[];
|
|
6
|
+
acceptanceCriteria: unknown[];
|
|
7
|
+
}
|
|
8
|
+
export declare function classifyTier(d: DraftSignals, tierConfig: CadenceConfig['tier']): Tier;
|
|
9
|
+
//# sourceMappingURL=tier.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tier.d.ts","sourceRoot":"","sources":["../../src/classify/tier.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,aAAa,EAAE,MAAM,6BAA6B,CAAC;AAEvE,MAAM,WAAW,YAAY;IAC3B,KAAK,EAAE;QAAE,KAAK,EAAE,MAAM,EAAE,CAAA;KAAE,EAAE,CAAC;IAC7B,kBAAkB,EAAE,OAAO,EAAE,CAAC;CAC/B;AAED,wBAAgB,YAAY,CAAC,CAAC,EAAE,YAAY,EAAE,UAAU,EAAE,aAAa,CAAC,MAAM,CAAC,GAAG,IAAI,CAkBrF"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
export function classifyTier(d, tierConfig) {
|
|
2
|
+
const taskCount = d.tasks.length;
|
|
3
|
+
const fileCount = new Set(d.tasks.flatMap((t) => t.files)).size;
|
|
4
|
+
if (taskCount <= tierConfig.quickFix.maxTasks &&
|
|
5
|
+
fileCount <= tierConfig.quickFix.maxFiles) {
|
|
6
|
+
return 'quick-fix';
|
|
7
|
+
}
|
|
8
|
+
if (taskCount <= tierConfig.standard.maxTasks &&
|
|
9
|
+
fileCount <= tierConfig.standard.maxFiles &&
|
|
10
|
+
taskCount < tierConfig.complex.minTasks) {
|
|
11
|
+
return 'standard';
|
|
12
|
+
}
|
|
13
|
+
return 'complex';
|
|
14
|
+
}
|
|
15
|
+
//# sourceMappingURL=tier.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tier.js","sourceRoot":"","sources":["../../src/classify/tier.ts"],"names":[],"mappings":"AAOA,MAAM,UAAU,YAAY,CAAC,CAAe,EAAE,UAAiC;IAC7E,MAAM,SAAS,GAAG,CAAC,CAAC,KAAK,CAAC,MAAM,CAAC;IACjC,MAAM,SAAS,GAAG,IAAI,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC;IAEhE,IACE,SAAS,IAAI,UAAU,CAAC,QAAQ,CAAC,QAAQ;QACzC,SAAS,IAAI,UAAU,CAAC,QAAQ,CAAC,QAAQ,EACzC,CAAC;QACD,OAAO,WAAW,CAAC;IACrB,CAAC;IACD,IACE,SAAS,IAAI,UAAU,CAAC,QAAQ,CAAC,QAAQ;QACzC,SAAS,IAAI,UAAU,CAAC,QAAQ,CAAC,QAAQ;QACzC,SAAS,GAAG,UAAU,CAAC,OAAO,CAAC,QAAQ,EACvC,CAAC;QACD,OAAO,UAAU,CAAC;IACpB,CAAC;IACD,OAAO,SAAS,CAAC;AACnB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"assumption.d.ts","sourceRoot":"","sources":["../../../src/cli/commands/assumption.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAyFzC,wBAAgB,yBAAyB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAgRhE"}
|
|
@@ -0,0 +1,313 @@
|
|
|
1
|
+
import { AssumptionZ } from '@manehorizons/cadence-types';
|
|
2
|
+
import { addAssumption, readAssumptionLedger, readRecommendationLedger, runAssumptionTransition, } from '../../intelligence/store.js';
|
|
3
|
+
import { renderAssumptionDetail } from '../../intelligence/render-assumption-detail.js';
|
|
4
|
+
function parseSortBy(raw) {
|
|
5
|
+
if (raw.length === 0)
|
|
6
|
+
return { error: '--sort-by requires a key' };
|
|
7
|
+
const colon = raw.indexOf(':');
|
|
8
|
+
if (colon === -1)
|
|
9
|
+
return { key: raw, dir: 'asc' };
|
|
10
|
+
const key = raw.slice(0, colon);
|
|
11
|
+
const dirRaw = raw.slice(colon + 1);
|
|
12
|
+
if (key.length === 0)
|
|
13
|
+
return { error: '--sort-by requires a key' };
|
|
14
|
+
if (dirRaw !== 'asc' && dirRaw !== 'desc') {
|
|
15
|
+
return { error: `invalid sort direction: '${dirRaw}' (use 'asc' or 'desc')` };
|
|
16
|
+
}
|
|
17
|
+
return { key, dir: dirRaw };
|
|
18
|
+
}
|
|
19
|
+
const ALLOWED_REGEX_FLAGS = new Set(['i', 'm', 's', 'u']);
|
|
20
|
+
function parseRegexFlags(raw) {
|
|
21
|
+
if (raw.length === 0)
|
|
22
|
+
return { error: '--filter-regex-flags requires a non-empty value' };
|
|
23
|
+
const seen = new Set();
|
|
24
|
+
for (const ch of raw) {
|
|
25
|
+
if (!ALLOWED_REGEX_FLAGS.has(ch)) {
|
|
26
|
+
return { error: `invalid flag letter: '${ch}' (allowed: i, m, s, u)` };
|
|
27
|
+
}
|
|
28
|
+
if (seen.has(ch)) {
|
|
29
|
+
return { error: `duplicate flag letter: '${ch}'` };
|
|
30
|
+
}
|
|
31
|
+
seen.add(ch);
|
|
32
|
+
}
|
|
33
|
+
return { flags: raw };
|
|
34
|
+
}
|
|
35
|
+
const ASN_SORT_KEYS = new Set(['created', 'status', 'text', 'rec']);
|
|
36
|
+
const ASN_STATUS_ORDER = [
|
|
37
|
+
'open',
|
|
38
|
+
'validated',
|
|
39
|
+
'rejected',
|
|
40
|
+
];
|
|
41
|
+
function compareAsn(a, b, key) {
|
|
42
|
+
switch (key) {
|
|
43
|
+
case 'created':
|
|
44
|
+
return a.createdAt < b.createdAt ? -1 : a.createdAt > b.createdAt ? 1 : 0;
|
|
45
|
+
case 'text':
|
|
46
|
+
return a.text < b.text ? -1 : a.text > b.text ? 1 : 0;
|
|
47
|
+
case 'rec':
|
|
48
|
+
return a.recommendationId < b.recommendationId
|
|
49
|
+
? -1
|
|
50
|
+
: a.recommendationId > b.recommendationId
|
|
51
|
+
? 1
|
|
52
|
+
: 0;
|
|
53
|
+
case 'status':
|
|
54
|
+
return ASN_STATUS_ORDER.indexOf(a.status) - ASN_STATUS_ORDER.indexOf(b.status);
|
|
55
|
+
default:
|
|
56
|
+
return 0;
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
const ASSUMPTION_TRANSITION_DESCRIPTIONS = {
|
|
60
|
+
validate: 'Mark an open assumption validated',
|
|
61
|
+
reject: 'Mark an open assumption rejected',
|
|
62
|
+
reopen: 'Reopen a validated or rejected assumption',
|
|
63
|
+
};
|
|
64
|
+
const ASSUMPTION_TRANSITION_PAST = {
|
|
65
|
+
validate: 'validated',
|
|
66
|
+
reject: 'rejected',
|
|
67
|
+
reopen: 'open',
|
|
68
|
+
};
|
|
69
|
+
export function registerAssumptionCommand(program) {
|
|
70
|
+
const cmd = program
|
|
71
|
+
.command('assumption')
|
|
72
|
+
.description('Manage CADENCE strategic-intelligence assumptions');
|
|
73
|
+
cmd
|
|
74
|
+
.command('add')
|
|
75
|
+
.description('Add a manual assumption tied to a recommendation')
|
|
76
|
+
.requiredOption('--rec <id>', 'Recommendation id this assumption belongs to')
|
|
77
|
+
.requiredOption('--text <text>', 'Assumption statement')
|
|
78
|
+
.action(async (opts) => {
|
|
79
|
+
try {
|
|
80
|
+
const a = await addAssumption(process.cwd(), {
|
|
81
|
+
recommendationId: opts.rec,
|
|
82
|
+
text: opts.text,
|
|
83
|
+
});
|
|
84
|
+
process.stdout.write(`Added ${a.id}: ${a.text}\n`);
|
|
85
|
+
process.stdout.write(`Next: cadence assumption list\n`);
|
|
86
|
+
}
|
|
87
|
+
catch (err) {
|
|
88
|
+
process.stderr.write(`assumption add failed: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
89
|
+
process.exitCode = 1;
|
|
90
|
+
}
|
|
91
|
+
});
|
|
92
|
+
cmd
|
|
93
|
+
.command('show <id>')
|
|
94
|
+
.description('Show a single assumption with its tied recommendation cross-ref')
|
|
95
|
+
.option('--format <format>', 'Output format: terminal | json', 'terminal')
|
|
96
|
+
.action(async (id, opts) => {
|
|
97
|
+
try {
|
|
98
|
+
const format = opts.format ?? 'terminal';
|
|
99
|
+
if (format !== 'terminal' && format !== 'json') {
|
|
100
|
+
process.stderr.write(`assumption show failed: unsupported format: ${format}\n`);
|
|
101
|
+
process.exitCode = 1;
|
|
102
|
+
return;
|
|
103
|
+
}
|
|
104
|
+
const asLedger = await readAssumptionLedger(process.cwd());
|
|
105
|
+
const as = asLedger.assumptions.find((a) => a.id === id);
|
|
106
|
+
if (!as) {
|
|
107
|
+
process.stderr.write(`assumption ${id} not found\n`);
|
|
108
|
+
process.exitCode = 1;
|
|
109
|
+
return;
|
|
110
|
+
}
|
|
111
|
+
const recLedger = await readRecommendationLedger(process.cwd());
|
|
112
|
+
const rec = recLedger.recommendations.find((r) => r.id === as.recommendationId);
|
|
113
|
+
if (format === 'json') {
|
|
114
|
+
const envelope = { assumption: as, recommendation: rec ?? null };
|
|
115
|
+
process.stdout.write(JSON.stringify(envelope, null, 2) + '\n');
|
|
116
|
+
return;
|
|
117
|
+
}
|
|
118
|
+
const md = renderAssumptionDetail(as, rec);
|
|
119
|
+
process.stdout.write(md);
|
|
120
|
+
if (!md.endsWith('\n'))
|
|
121
|
+
process.stdout.write('\n');
|
|
122
|
+
}
|
|
123
|
+
catch (err) {
|
|
124
|
+
process.stderr.write(`assumption show failed: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
125
|
+
process.exitCode = 1;
|
|
126
|
+
}
|
|
127
|
+
});
|
|
128
|
+
cmd
|
|
129
|
+
.command('list')
|
|
130
|
+
.description('List recorded assumptions')
|
|
131
|
+
.option('--format <format>', 'Output format: terminal | json', 'terminal')
|
|
132
|
+
.option('--filter-status <status>', 'Filter to only entries with this status')
|
|
133
|
+
.option('--filter-rec <recId>', 'Filter to only entries tied to this recommendation')
|
|
134
|
+
.option('--filter-text <substr>', 'Case-insensitive substring search on text. Mutually exclusive with --filter-text-exact and --filter-regex.')
|
|
135
|
+
.option('--filter-text-exact <str>', 'Case-insensitive whole-field equality match on text. Mutually exclusive with --filter-text and --filter-regex.')
|
|
136
|
+
.option('--filter-regex <pattern>', 'Power-user regex filter on text (always case-sensitive by default; use --filter-regex-flags for case-insensitive/multiline/dotAll, or character classes like [Cc]ycle for one-off case-insensitivity). Mutually exclusive with --filter-text and --filter-text-exact.')
|
|
137
|
+
.option('--filter-regex-flags <flags>', 'RegExp flag letters to apply to --filter-regex. Allowed: i (case-insensitive), m (multiline ^/$), s (dotAll .), u (unicode). Requires --filter-regex.')
|
|
138
|
+
.option('--sort-by <key>', 'Sort by a single key, optionally with :desc suffix. Allowed keys: created, status, text, rec.')
|
|
139
|
+
.option('--reverse', 'Reverse the entry order (after filters, before offset/limit)')
|
|
140
|
+
.option('--offset <n>', 'Skip the first N entries (after filters)')
|
|
141
|
+
.option('--limit <n>', 'Cap output to first N entries (after filters)')
|
|
142
|
+
.action(async (opts) => {
|
|
143
|
+
try {
|
|
144
|
+
const format = opts.format ?? 'terminal';
|
|
145
|
+
if (format !== 'terminal' && format !== 'json') {
|
|
146
|
+
process.stderr.write(`assumption list failed: unsupported format: ${format}\n`);
|
|
147
|
+
process.exitCode = 1;
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
const ledger = await readAssumptionLedger(process.cwd());
|
|
151
|
+
let entries = ledger.assumptions;
|
|
152
|
+
if (opts.filterStatus !== undefined) {
|
|
153
|
+
const parsed = AssumptionZ.shape.status.safeParse(opts.filterStatus);
|
|
154
|
+
if (!parsed.success) {
|
|
155
|
+
process.stderr.write(`assumption list failed: invalid status: ${opts.filterStatus}\n`);
|
|
156
|
+
process.exitCode = 1;
|
|
157
|
+
return;
|
|
158
|
+
}
|
|
159
|
+
entries = entries.filter((a) => a.status === parsed.data);
|
|
160
|
+
}
|
|
161
|
+
if (opts.filterRec !== undefined) {
|
|
162
|
+
entries = entries.filter((a) => a.recommendationId === opts.filterRec);
|
|
163
|
+
}
|
|
164
|
+
if (opts.filterTextExact === '') {
|
|
165
|
+
process.stderr.write(`assumption list failed: --filter-text-exact requires a non-empty value\n`);
|
|
166
|
+
process.exitCode = 1;
|
|
167
|
+
return;
|
|
168
|
+
}
|
|
169
|
+
if (opts.filterTextExact !== undefined && opts.filterText !== undefined) {
|
|
170
|
+
process.stderr.write(`assumption list failed: cannot combine --filter-text-exact with --filter-text\n`);
|
|
171
|
+
process.exitCode = 1;
|
|
172
|
+
return;
|
|
173
|
+
}
|
|
174
|
+
if (opts.filterTextExact !== undefined && opts.filterRegex !== undefined) {
|
|
175
|
+
process.stderr.write(`assumption list failed: cannot combine --filter-text-exact with --filter-regex\n`);
|
|
176
|
+
process.exitCode = 1;
|
|
177
|
+
return;
|
|
178
|
+
}
|
|
179
|
+
if (opts.filterText !== undefined && opts.filterRegex !== undefined) {
|
|
180
|
+
process.stderr.write(`assumption list failed: cannot combine --filter-text and --filter-regex\n`);
|
|
181
|
+
process.exitCode = 1;
|
|
182
|
+
return;
|
|
183
|
+
}
|
|
184
|
+
if (opts.filterText !== undefined) {
|
|
185
|
+
const needle = opts.filterText.toLowerCase();
|
|
186
|
+
entries = entries.filter((a) => a.text.toLowerCase().includes(needle));
|
|
187
|
+
}
|
|
188
|
+
if (opts.filterRegexFlags !== undefined && opts.filterRegex === undefined) {
|
|
189
|
+
process.stderr.write(`assumption list failed: --filter-regex-flags requires --filter-regex to also be set\n`);
|
|
190
|
+
process.exitCode = 1;
|
|
191
|
+
return;
|
|
192
|
+
}
|
|
193
|
+
let regexFlags;
|
|
194
|
+
if (opts.filterRegexFlags !== undefined) {
|
|
195
|
+
const parsed = parseRegexFlags(opts.filterRegexFlags);
|
|
196
|
+
if ('error' in parsed) {
|
|
197
|
+
process.stderr.write(`assumption list failed: ${parsed.error}\n`);
|
|
198
|
+
process.exitCode = 1;
|
|
199
|
+
return;
|
|
200
|
+
}
|
|
201
|
+
regexFlags = parsed.flags;
|
|
202
|
+
}
|
|
203
|
+
if (opts.filterRegex !== undefined) {
|
|
204
|
+
let regex;
|
|
205
|
+
try {
|
|
206
|
+
regex = new RegExp(opts.filterRegex, regexFlags);
|
|
207
|
+
}
|
|
208
|
+
catch (err) {
|
|
209
|
+
process.stderr.write(`assumption list failed: invalid regex: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
210
|
+
process.exitCode = 1;
|
|
211
|
+
return;
|
|
212
|
+
}
|
|
213
|
+
entries = entries.filter((a) => regex.test(a.text));
|
|
214
|
+
}
|
|
215
|
+
if (opts.filterTextExact !== undefined) {
|
|
216
|
+
const needle = opts.filterTextExact.toLowerCase();
|
|
217
|
+
entries = entries.filter((a) => a.text.toLowerCase() === needle);
|
|
218
|
+
}
|
|
219
|
+
if (opts.sortBy !== undefined) {
|
|
220
|
+
const parsed = parseSortBy(opts.sortBy);
|
|
221
|
+
if ('error' in parsed) {
|
|
222
|
+
process.stderr.write(`assumption list failed: ${parsed.error}\n`);
|
|
223
|
+
process.exitCode = 1;
|
|
224
|
+
return;
|
|
225
|
+
}
|
|
226
|
+
if (!ASN_SORT_KEYS.has(parsed.key)) {
|
|
227
|
+
const allowed = [...ASN_SORT_KEYS].join(', ');
|
|
228
|
+
process.stderr.write(`assumption list failed: invalid sort key: ${parsed.key} (allowed: ${allowed})\n`);
|
|
229
|
+
process.exitCode = 1;
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
232
|
+
const sortKey = parsed.key;
|
|
233
|
+
const dir = parsed.dir;
|
|
234
|
+
entries = entries.slice().sort((a, b) => dir === 'desc' ? -compareAsn(a, b, sortKey) : compareAsn(a, b, sortKey));
|
|
235
|
+
}
|
|
236
|
+
if (opts.reverse) {
|
|
237
|
+
entries = entries.slice().reverse();
|
|
238
|
+
}
|
|
239
|
+
if (opts.offset !== undefined) {
|
|
240
|
+
const n = Number(opts.offset);
|
|
241
|
+
if (!Number.isInteger(n) || n < 0) {
|
|
242
|
+
process.stderr.write(`assumption list failed: invalid offset: ${opts.offset}\n`);
|
|
243
|
+
process.exitCode = 1;
|
|
244
|
+
return;
|
|
245
|
+
}
|
|
246
|
+
entries = entries.slice(n);
|
|
247
|
+
}
|
|
248
|
+
if (opts.limit !== undefined) {
|
|
249
|
+
const n = Number(opts.limit);
|
|
250
|
+
if (!Number.isInteger(n) || n < 1) {
|
|
251
|
+
process.stderr.write(`assumption list failed: invalid limit: ${opts.limit}\n`);
|
|
252
|
+
process.exitCode = 1;
|
|
253
|
+
return;
|
|
254
|
+
}
|
|
255
|
+
entries = entries.slice(0, n);
|
|
256
|
+
}
|
|
257
|
+
if (format === 'json') {
|
|
258
|
+
process.stdout.write(JSON.stringify(entries, null, 2) + '\n');
|
|
259
|
+
return;
|
|
260
|
+
}
|
|
261
|
+
if (entries.length === 0) {
|
|
262
|
+
const filterDims = [];
|
|
263
|
+
if (opts.filterStatus)
|
|
264
|
+
filterDims.push(`status=${opts.filterStatus}`);
|
|
265
|
+
if (opts.filterRec)
|
|
266
|
+
filterDims.push(`rec=${opts.filterRec}`);
|
|
267
|
+
if (opts.filterText !== undefined)
|
|
268
|
+
filterDims.push(`text="${opts.filterText}"`);
|
|
269
|
+
if (opts.filterTextExact !== undefined)
|
|
270
|
+
filterDims.push(`text-exact="${opts.filterTextExact}"`);
|
|
271
|
+
if (opts.filterRegex !== undefined)
|
|
272
|
+
filterDims.push(`regex="${opts.filterRegex}"`);
|
|
273
|
+
if (opts.filterRegexFlags !== undefined)
|
|
274
|
+
filterDims.push(`regex-flags="${opts.filterRegexFlags}"`);
|
|
275
|
+
if (opts.offset !== undefined)
|
|
276
|
+
filterDims.push(`offset=${opts.offset}`);
|
|
277
|
+
const msg = filterDims.length > 0
|
|
278
|
+
? `No assumptions matching ${filterDims.join(', ')} recorded.\n`
|
|
279
|
+
: 'No assumptions recorded.\n';
|
|
280
|
+
process.stdout.write(msg);
|
|
281
|
+
return;
|
|
282
|
+
}
|
|
283
|
+
for (const a of entries) {
|
|
284
|
+
process.stdout.write(`${a.id} ${a.status} ${a.recommendationId} ${a.text}\n`);
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
catch (err) {
|
|
288
|
+
process.stderr.write(`assumption list failed: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
289
|
+
process.exitCode = 1;
|
|
290
|
+
}
|
|
291
|
+
});
|
|
292
|
+
for (const action of ['validate', 'reject', 'reopen']) {
|
|
293
|
+
cmd
|
|
294
|
+
.command(`${action} <id>`)
|
|
295
|
+
.description(ASSUMPTION_TRANSITION_DESCRIPTIONS[action])
|
|
296
|
+
.action(async (id) => {
|
|
297
|
+
try {
|
|
298
|
+
const res = await runAssumptionTransition(process.cwd(), id, action);
|
|
299
|
+
if (!res.ok) {
|
|
300
|
+
process.stderr.write(`assumption ${action} refused: ${res.error}\n`);
|
|
301
|
+
process.exitCode = 1;
|
|
302
|
+
return;
|
|
303
|
+
}
|
|
304
|
+
process.stdout.write(`assumption ${id} → ${ASSUMPTION_TRANSITION_PAST[action]}\n`);
|
|
305
|
+
}
|
|
306
|
+
catch (err) {
|
|
307
|
+
process.stderr.write(`assumption ${action} failed: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
308
|
+
process.exitCode = 1;
|
|
309
|
+
}
|
|
310
|
+
});
|
|
311
|
+
}
|
|
312
|
+
}
|
|
313
|
+
//# sourceMappingURL=assumption.js.map
|