@dommaker/harness 1.3.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +20 -0
- package/README.md +0 -2
- package/bin/harness.js +86 -32
- package/dist/cli/command-contract.d.ts +83 -0
- package/dist/cli/command-contract.d.ts.map +1 -0
- package/dist/cli/command-contract.js +66 -0
- package/dist/cli/command-contract.js.map +1 -0
- package/dist/cli/commands/acceptance.d.ts +3 -2
- package/dist/cli/commands/acceptance.d.ts.map +1 -1
- package/dist/cli/commands/acceptance.js +28 -24
- package/dist/cli/commands/acceptance.js.map +1 -1
- package/dist/cli/commands/analyze-sessions.d.ts +2 -1
- package/dist/cli/commands/analyze-sessions.d.ts.map +1 -1
- package/dist/cli/commands/analyze-sessions.js +25 -24
- package/dist/cli/commands/analyze-sessions.js.map +1 -1
- package/dist/cli/commands/check.d.ts +14 -2
- package/dist/cli/commands/check.d.ts.map +1 -1
- package/dist/cli/commands/check.js +104 -61
- package/dist/cli/commands/check.js.map +1 -1
- package/dist/cli/commands/command.d.ts +5 -1
- package/dist/cli/commands/command.d.ts.map +1 -1
- package/dist/cli/commands/command.js +26 -17
- package/dist/cli/commands/command.js.map +1 -1
- package/dist/cli/commands/constraints-report.d.ts +2 -1
- package/dist/cli/commands/constraints-report.d.ts.map +1 -1
- package/dist/cli/commands/constraints-report.js +37 -33
- package/dist/cli/commands/constraints-report.js.map +1 -1
- package/dist/cli/commands/constraints-retire.d.ts +6 -5
- package/dist/cli/commands/constraints-retire.d.ts.map +1 -1
- package/dist/cli/commands/constraints-retire.js +50 -52
- package/dist/cli/commands/constraints-retire.js.map +1 -1
- package/dist/cli/commands/constraints.d.ts +2 -1
- package/dist/cli/commands/constraints.d.ts.map +1 -1
- package/dist/cli/commands/constraints.js +10 -27
- package/dist/cli/commands/constraints.js.map +1 -1
- package/dist/cli/commands/contract.d.ts +3 -2
- package/dist/cli/commands/contract.d.ts.map +1 -1
- package/dist/cli/commands/contract.js +45 -42
- package/dist/cli/commands/contract.js.map +1 -1
- package/dist/cli/commands/definitions.d.ts +11 -11
- package/dist/cli/commands/definitions.d.ts.map +1 -1
- package/dist/cli/commands/definitions.js +27 -219
- package/dist/cli/commands/definitions.js.map +1 -1
- package/dist/cli/commands/failure.d.ts +5 -4
- package/dist/cli/commands/failure.d.ts.map +1 -1
- package/dist/cli/commands/failure.js +31 -25
- package/dist/cli/commands/failure.js.map +1 -1
- package/dist/cli/commands/init.d.ts +7 -5
- package/dist/cli/commands/init.d.ts.map +1 -1
- package/dist/cli/commands/init.js +147 -211
- package/dist/cli/commands/init.js.map +1 -1
- package/dist/cli/commands/knowledge.d.ts +17 -30
- package/dist/cli/commands/knowledge.d.ts.map +1 -1
- package/dist/cli/commands/knowledge.js +183 -273
- package/dist/cli/commands/knowledge.js.map +1 -1
- package/dist/cli/commands/passes-gate.d.ts +8 -2
- package/dist/cli/commands/passes-gate.d.ts.map +1 -1
- package/dist/cli/commands/passes-gate.js +44 -66
- package/dist/cli/commands/passes-gate.js.map +1 -1
- package/dist/cli/commands/performance.d.ts +2 -1
- package/dist/cli/commands/performance.d.ts.map +1 -1
- package/dist/cli/commands/performance.js +20 -18
- package/dist/cli/commands/performance.js.map +1 -1
- package/dist/cli/commands/posteval-plan.d.ts +5 -1
- package/dist/cli/commands/posteval-plan.d.ts.map +1 -1
- package/dist/cli/commands/posteval-plan.js +26 -15
- package/dist/cli/commands/posteval-plan.js.map +1 -1
- package/dist/cli/commands/release.d.ts +6 -1
- package/dist/cli/commands/release.d.ts.map +1 -1
- package/dist/cli/commands/release.js +69 -59
- package/dist/cli/commands/release.js.map +1 -1
- package/dist/cli/commands/report.d.ts +2 -1
- package/dist/cli/commands/report.d.ts.map +1 -1
- package/dist/cli/commands/report.js +9 -5
- package/dist/cli/commands/report.js.map +1 -1
- package/dist/cli/commands/review.d.ts +3 -2
- package/dist/cli/commands/review.d.ts.map +1 -1
- package/dist/cli/commands/review.js +33 -29
- package/dist/cli/commands/review.js.map +1 -1
- package/dist/cli/commands/sdd.d.ts +2 -1
- package/dist/cli/commands/sdd.d.ts.map +1 -1
- package/dist/cli/commands/sdd.js +7 -5
- package/dist/cli/commands/sdd.js.map +1 -1
- package/dist/cli/commands/security.d.ts +3 -2
- package/dist/cli/commands/security.d.ts.map +1 -1
- package/dist/cli/commands/security.js +29 -26
- package/dist/cli/commands/security.js.map +1 -1
- package/dist/cli/commands/spec-baseline-check.d.ts +2 -1
- package/dist/cli/commands/spec-baseline-check.d.ts.map +1 -1
- package/dist/cli/commands/spec-baseline-check.js +15 -11
- package/dist/cli/commands/spec-baseline-check.js.map +1 -1
- package/dist/cli/commands/spec.d.ts +7 -2
- package/dist/cli/commands/spec.d.ts.map +1 -1
- package/dist/cli/commands/spec.js +61 -51
- package/dist/cli/commands/spec.js.map +1 -1
- package/dist/cli/commands/status.d.ts +2 -1
- package/dist/cli/commands/status.d.ts.map +1 -1
- package/dist/cli/commands/status.js +57 -53
- package/dist/cli/commands/status.js.map +1 -1
- package/dist/cli/commands/sync-docs/agents-syncer.d.ts.map +1 -1
- package/dist/cli/commands/sync-docs/agents-syncer.js +5 -2
- package/dist/cli/commands/sync-docs/agents-syncer.js.map +1 -1
- package/dist/cli/commands/sync-docs/context-syncer.d.ts.map +1 -1
- package/dist/cli/commands/sync-docs/context-syncer.js +3 -2
- package/dist/cli/commands/sync-docs/context-syncer.js.map +1 -1
- package/dist/cli/commands/sync-docs/index.d.ts +2 -1
- package/dist/cli/commands/sync-docs/index.d.ts.map +1 -1
- package/dist/cli/commands/sync-docs/index.js +68 -88
- package/dist/cli/commands/sync-docs/index.js.map +1 -1
- package/dist/cli/commands/sync-docs/project-reader.d.ts +6 -1
- package/dist/cli/commands/sync-docs/project-reader.d.ts.map +1 -1
- package/dist/cli/commands/sync-docs/project-reader.js +14 -16
- package/dist/cli/commands/sync-docs/project-reader.js.map +1 -1
- package/dist/cli/commands/update-user-model.d.ts +9 -3
- package/dist/cli/commands/update-user-model.d.ts.map +1 -1
- package/dist/cli/commands/update-user-model.js +56 -61
- package/dist/cli/commands/update-user-model.js.map +1 -1
- package/dist/cli/commands/validate.d.ts +4 -3
- package/dist/cli/commands/validate.d.ts.map +1 -1
- package/dist/cli/commands/validate.js +28 -26
- package/dist/cli/commands/validate.js.map +1 -1
- package/dist/cli/session-mining/transcript.d.ts +7 -1
- package/dist/cli/session-mining/transcript.d.ts.map +1 -1
- package/dist/cli/session-mining/transcript.js +21 -14
- package/dist/cli/session-mining/transcript.js.map +1 -1
- package/dist/context/session-manager.d.ts.map +1 -1
- package/dist/context/session-manager.js +19 -32
- package/dist/context/session-manager.js.map +1 -1
- package/dist/core/constraints/agent-prompt-renderer.d.ts.map +1 -1
- package/dist/core/constraints/agent-prompt-renderer.js +1 -4
- package/dist/core/constraints/agent-prompt-renderer.js.map +1 -1
- package/dist/core/constraints/capabilities-parser.d.ts +24 -7
- package/dist/core/constraints/capabilities-parser.d.ts.map +1 -1
- package/dist/core/constraints/capabilities-parser.js +32 -28
- package/dist/core/constraints/capabilities-parser.js.map +1 -1
- package/dist/core/constraints/capabilities-reconcile.d.ts +67 -0
- package/dist/core/constraints/capabilities-reconcile.d.ts.map +1 -0
- package/dist/core/constraints/capabilities-reconcile.js +105 -0
- package/dist/core/constraints/capabilities-reconcile.js.map +1 -0
- package/dist/core/constraints/checker.d.ts +21 -43
- package/dist/core/constraints/checker.d.ts.map +1 -1
- package/dist/core/constraints/checker.js +68 -117
- package/dist/core/constraints/checker.js.map +1 -1
- package/dist/core/constraints/checkers/capability-sync.d.ts +20 -8
- package/dist/core/constraints/checkers/capability-sync.d.ts.map +1 -1
- package/dist/core/constraints/checkers/capability-sync.js +66 -77
- package/dist/core/constraints/checkers/capability-sync.js.map +1 -1
- package/dist/core/constraints/checkers/context-doc-sync.d.ts +4 -2
- package/dist/core/constraints/checkers/context-doc-sync.d.ts.map +1 -1
- package/dist/core/constraints/checkers/context-doc-sync.js +13 -22
- package/dist/core/constraints/checkers/context-doc-sync.js.map +1 -1
- package/dist/core/constraints/checkers/docs-freshness.d.ts.map +1 -1
- package/dist/core/constraints/checkers/docs-freshness.js +49 -66
- package/dist/core/constraints/checkers/docs-freshness.js.map +1 -1
- package/dist/core/constraints/checkers/governance-presence.d.ts +2 -2
- package/dist/core/constraints/checkers/governance-presence.d.ts.map +1 -1
- package/dist/core/constraints/checkers/governance-presence.js +7 -28
- package/dist/core/constraints/checkers/governance-presence.js.map +1 -1
- package/dist/core/constraints/checkers/index.d.ts +2 -2
- package/dist/core/constraints/checkers/index.d.ts.map +1 -1
- package/dist/core/constraints/checkers/index.js +2 -1
- package/dist/core/constraints/checkers/index.js.map +1 -1
- package/dist/core/constraints/checkers/no-test-simplification.d.ts.map +1 -1
- package/dist/core/constraints/checkers/no-test-simplification.js +4 -3
- package/dist/core/constraints/checkers/no-test-simplification.js.map +1 -1
- package/dist/core/constraints/checkers/types.d.ts +43 -4
- package/dist/core/constraints/checkers/types.d.ts.map +1 -1
- package/dist/core/constraints/checkers/types.js +33 -0
- package/dist/core/constraints/checkers/types.js.map +1 -1
- package/dist/core/constraints/context-builder.d.ts +15 -14
- package/dist/core/constraints/context-builder.d.ts.map +1 -1
- package/dist/core/constraints/context-builder.js +32 -96
- package/dist/core/constraints/context-builder.js.map +1 -1
- package/dist/core/constraints/doc-freshness/runner.d.ts.map +1 -1
- package/dist/core/constraints/doc-freshness/runner.js +2 -1
- package/dist/core/constraints/doc-freshness/runner.js.map +1 -1
- package/dist/core/constraints/git-evidence.d.ts +60 -0
- package/dist/core/constraints/git-evidence.d.ts.map +1 -0
- package/dist/core/constraints/git-evidence.js +88 -0
- package/dist/core/constraints/git-evidence.js.map +1 -0
- package/dist/core/constraints/injection-drift.d.ts +3 -20
- package/dist/core/constraints/injection-drift.d.ts.map +1 -1
- package/dist/core/constraints/injection-drift.js +10 -57
- package/dist/core/constraints/injection-drift.js.map +1 -1
- package/dist/core/constraints/injection-writer.d.ts +113 -0
- package/dist/core/constraints/injection-writer.d.ts.map +1 -0
- package/dist/core/constraints/injection-writer.js +228 -0
- package/dist/core/constraints/injection-writer.js.map +1 -0
- package/dist/core/constraints/usage-report.d.ts +22 -1
- package/dist/core/constraints/usage-report.d.ts.map +1 -1
- package/dist/core/constraints/usage-report.js +27 -20
- package/dist/core/constraints/usage-report.js.map +1 -1
- package/dist/core/index.d.ts +2 -2
- package/dist/core/index.d.ts.map +1 -1
- package/dist/core/index.js +4 -2
- package/dist/core/index.js.map +1 -1
- package/dist/core/project-config-loader.d.ts +32 -1
- package/dist/core/project-config-loader.d.ts.map +1 -1
- package/dist/core/project-config-loader.js +39 -9
- package/dist/core/project-config-loader.js.map +1 -1
- package/dist/core/validators/passes-gate.d.ts +15 -64
- package/dist/core/validators/passes-gate.d.ts.map +1 -1
- package/dist/core/validators/passes-gate.js +84 -222
- package/dist/core/validators/passes-gate.js.map +1 -1
- package/dist/core/validators/test-output.d.ts +58 -0
- package/dist/core/validators/test-output.d.ts.map +1 -0
- package/dist/core/validators/test-output.js +109 -0
- package/dist/core/validators/test-output.js.map +1 -0
- package/dist/failure/recorder.d.ts +6 -0
- package/dist/failure/recorder.d.ts.map +1 -1
- package/dist/failure/recorder.js +12 -8
- package/dist/failure/recorder.js.map +1 -1
- package/dist/gates/acceptance.d.ts +1 -48
- package/dist/gates/acceptance.d.ts.map +1 -1
- package/dist/gates/acceptance.js +6 -38
- package/dist/gates/acceptance.js.map +1 -1
- package/dist/gates/checker-gate.d.ts +2 -1
- package/dist/gates/checker-gate.d.ts.map +1 -1
- package/dist/gates/checker-gate.js +11 -13
- package/dist/gates/checker-gate.js.map +1 -1
- package/dist/gates/command.d.ts.map +1 -1
- package/dist/gates/command.js +10 -22
- package/dist/gates/command.js.map +1 -1
- package/dist/gates/contract.d.ts.map +1 -1
- package/dist/gates/contract.js +22 -61
- package/dist/gates/contract.js.map +1 -1
- package/dist/gates/performance.d.ts.map +1 -1
- package/dist/gates/performance.js +13 -31
- package/dist/gates/performance.js.map +1 -1
- package/dist/gates/review.d.ts.map +1 -1
- package/dist/gates/review.js +21 -53
- package/dist/gates/review.js.map +1 -1
- package/dist/gates/security.d.ts.map +1 -1
- package/dist/gates/security.js +14 -32
- package/dist/gates/security.js.map +1 -1
- package/dist/gates/types.d.ts +28 -5
- package/dist/gates/types.d.ts.map +1 -1
- package/dist/gates/types.js +38 -1
- package/dist/gates/types.js.map +1 -1
- package/dist/hooks/bootstrap.d.ts +2 -0
- package/dist/hooks/bootstrap.d.ts.map +1 -1
- package/dist/hooks/bootstrap.js +5 -2
- package/dist/hooks/bootstrap.js.map +1 -1
- package/dist/index.d.ts +1 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js.map +1 -1
- package/dist/knowledge/audit.d.ts +7 -2
- package/dist/knowledge/audit.d.ts.map +1 -1
- package/dist/knowledge/audit.js +59 -79
- package/dist/knowledge/audit.js.map +1 -1
- package/dist/knowledge/flywheel-metrics.d.ts +39 -0
- package/dist/knowledge/flywheel-metrics.d.ts.map +1 -0
- package/dist/knowledge/flywheel-metrics.js +47 -0
- package/dist/knowledge/flywheel-metrics.js.map +1 -0
- package/dist/knowledge/import.d.ts.map +1 -1
- package/dist/knowledge/import.js +4 -14
- package/dist/knowledge/import.js.map +1 -1
- package/dist/knowledge/index-generator.d.ts.map +1 -1
- package/dist/knowledge/index-generator.js +17 -14
- package/dist/knowledge/index-generator.js.map +1 -1
- package/dist/knowledge/ingest.d.ts.map +1 -1
- package/dist/knowledge/ingest.js +9 -4
- package/dist/knowledge/ingest.js.map +1 -1
- package/dist/knowledge/migration.d.ts.map +1 -1
- package/dist/knowledge/migration.js +11 -8
- package/dist/knowledge/migration.js.map +1 -1
- package/dist/knowledge/reference-tracker.d.ts.map +1 -1
- package/dist/knowledge/reference-tracker.js +12 -9
- package/dist/knowledge/reference-tracker.js.map +1 -1
- package/dist/knowledge/store.d.ts +15 -0
- package/dist/knowledge/store.d.ts.map +1 -1
- package/dist/knowledge/store.js +59 -10
- package/dist/knowledge/store.js.map +1 -1
- package/dist/monitoring/context-tracker.d.ts.map +1 -1
- package/dist/monitoring/context-tracker.js +11 -20
- package/dist/monitoring/context-tracker.js.map +1 -1
- package/dist/monitoring/index.d.ts +1 -1
- package/dist/monitoring/index.d.ts.map +1 -1
- package/dist/monitoring/index.js +1 -2
- package/dist/monitoring/index.js.map +1 -1
- package/dist/monitoring/trace-analyzer.d.ts +15 -0
- package/dist/monitoring/trace-analyzer.d.ts.map +1 -1
- package/dist/monitoring/trace-analyzer.js +19 -2
- package/dist/monitoring/trace-analyzer.js.map +1 -1
- package/dist/monitoring/traces.d.ts +21 -2
- package/dist/monitoring/traces.d.ts.map +1 -1
- package/dist/monitoring/traces.js +38 -29
- package/dist/monitoring/traces.js.map +1 -1
- package/dist/release/index.d.ts +2 -2
- package/dist/release/index.d.ts.map +1 -1
- package/dist/release/index.js +1 -5
- package/dist/release/index.js.map +1 -1
- package/dist/sdd/index-generator.js +10 -11
- package/dist/sdd/index-generator.js.map +1 -1
- package/dist/test-setup/project-fixture.d.ts +48 -0
- package/dist/test-setup/project-fixture.d.ts.map +1 -0
- package/dist/test-setup/project-fixture.js +106 -0
- package/dist/test-setup/project-fixture.js.map +1 -0
- package/dist/types/constraint.d.ts +8 -18
- package/dist/types/constraint.d.ts.map +1 -1
- package/dist/types/constraint.js +6 -1
- package/dist/types/constraint.js.map +1 -1
- package/dist/types/passes-gate.d.ts +10 -25
- package/dist/types/passes-gate.d.ts.map +1 -1
- package/dist/types/project-config.d.ts +1 -1
- package/dist/types/session.d.ts +6 -5
- package/dist/types/session.d.ts.map +1 -1
- package/dist/types/trace.d.ts +9 -0
- package/dist/types/trace.d.ts.map +1 -1
- package/dist/utils/exec.d.ts +10 -0
- package/dist/utils/exec.d.ts.map +1 -1
- package/dist/utils/exec.js +12 -0
- package/dist/utils/exec.js.map +1 -1
- package/dist/utils/file-walk.d.ts +9 -1
- package/dist/utils/file-walk.d.ts.map +1 -1
- package/dist/utils/file-walk.js +10 -1
- package/dist/utils/file-walk.js.map +1 -1
- package/dist/utils/frontmatter.d.ts +73 -0
- package/dist/utils/frontmatter.d.ts.map +1 -0
- package/dist/utils/frontmatter.js +141 -0
- package/dist/utils/frontmatter.js.map +1 -0
- package/dist/utils/jsonl.d.ts +92 -0
- package/dist/utils/jsonl.d.ts.map +1 -0
- package/dist/utils/jsonl.js +166 -0
- package/dist/utils/jsonl.js.map +1 -0
- package/dist/utils/package-version.d.ts +16 -0
- package/dist/utils/package-version.d.ts.map +1 -0
- package/dist/utils/package-version.js +63 -0
- package/dist/utils/package-version.js.map +1 -0
- package/package.json +1 -1
- package/src/CONTEXT.md +8 -2
- package/src/__tests__/acceptance-gate.test.ts +3 -1
- package/src/__tests__/checker-extra.test.ts +7 -1218
- package/src/__tests__/context-files-resolution.test.ts +116 -0
- package/src/__tests__/effective-constraints.test.ts +10 -13
- package/src/__tests__/exec.test.ts +35 -1
- package/src/__tests__/layering.test.ts +152 -0
- package/src/__tests__/passes-gate-extra.test.ts +0 -145
- package/src/__tests__/passes-gate.test.ts +130 -101
- package/src/__tests__/skip-semantics.test.ts +5 -9
- package/src/cli/__tests__/command-contract.test.ts +170 -0
- package/src/cli/command-contract.ts +108 -0
- package/src/cli/commands/CONTEXT.md +23 -8
- package/src/cli/commands/__tests__/acceptance.test.ts +40 -33
- package/src/cli/commands/__tests__/analyze-sessions.test.ts +35 -29
- package/src/cli/commands/__tests__/bin-exit-mapping.test.ts +107 -0
- package/src/cli/commands/__tests__/check-drift.test.ts +27 -34
- package/src/cli/commands/__tests__/check-skip-output.test.ts +21 -24
- package/src/cli/commands/__tests__/check.test.ts +448 -378
- package/src/cli/commands/__tests__/command.test.ts +85 -70
- package/src/cli/commands/__tests__/constraints-report.test.ts +100 -71
- package/src/cli/commands/__tests__/constraints-retire.test.ts +152 -95
- package/src/cli/commands/__tests__/contract.test.ts +27 -34
- package/src/cli/commands/__tests__/failure.test.ts +31 -34
- package/src/cli/commands/__tests__/init-injection.test.ts +58 -28
- package/src/cli/commands/__tests__/init.test.ts +77 -48
- package/src/cli/commands/__tests__/knowledge-flywheel-consistency.test.ts +108 -0
- package/src/cli/commands/__tests__/knowledge.test.ts +69 -43
- package/src/cli/commands/__tests__/passes-gate.test.ts +43 -45
- package/src/cli/commands/__tests__/performance.test.ts +22 -23
- package/src/cli/commands/__tests__/posteval-plan.test.ts +39 -38
- package/src/cli/commands/__tests__/project-path-anchoring.test.ts +157 -0
- package/src/cli/commands/__tests__/project-path-convention.test.ts +231 -0
- package/src/cli/commands/__tests__/registry.test.ts +75 -35
- package/src/cli/commands/__tests__/release.test.ts +209 -80
- package/src/cli/commands/__tests__/report-extra.test.ts +16 -16
- package/src/cli/commands/__tests__/report.test.ts +25 -25
- package/src/cli/commands/__tests__/review.test.ts +33 -31
- package/src/cli/commands/__tests__/security.test.ts +23 -27
- package/src/cli/commands/__tests__/spec-baseline-check.test.ts +20 -20
- package/src/cli/commands/__tests__/spec.test.ts +41 -29
- package/src/cli/commands/__tests__/status-extra.test.ts +18 -18
- package/src/cli/commands/__tests__/status-skipped-lines.test.ts +72 -0
- package/src/cli/commands/__tests__/status.test.ts +34 -34
- package/src/cli/commands/__tests__/sync-docs-agents.test.ts +77 -78
- package/src/cli/commands/__tests__/sync-docs.test.ts +72 -74
- package/src/cli/commands/__tests__/update-user-model.test.ts +97 -34
- package/src/cli/commands/__tests__/validate.test.ts +27 -29
- package/src/cli/commands/acceptance.ts +35 -24
- package/src/cli/commands/analyze-sessions.ts +25 -24
- package/src/cli/commands/check.ts +127 -66
- package/src/cli/commands/command.ts +30 -17
- package/src/cli/commands/constraints-report.ts +37 -34
- package/src/cli/commands/constraints-retire.ts +58 -55
- package/src/cli/commands/constraints.ts +10 -27
- package/src/cli/commands/contract.ts +51 -42
- package/src/cli/commands/definitions.ts +34 -227
- package/src/cli/commands/failure.ts +33 -26
- package/src/cli/commands/init.ts +166 -220
- package/src/cli/commands/knowledge.ts +192 -289
- package/src/cli/commands/passes-gate.ts +58 -68
- package/src/cli/commands/performance.ts +23 -18
- package/src/cli/commands/posteval-plan.ts +29 -15
- package/src/cli/commands/release.ts +70 -59
- package/src/cli/commands/report.ts +9 -5
- package/src/cli/commands/review.ts +39 -29
- package/src/cli/commands/sdd.ts +7 -5
- package/src/cli/commands/security.ts +35 -26
- package/src/cli/commands/spec-baseline-check.ts +16 -11
- package/src/cli/commands/spec.ts +66 -53
- package/src/cli/commands/status.ts +59 -53
- package/src/cli/commands/sync-docs/agents-syncer.ts +5 -2
- package/src/cli/commands/sync-docs/context-syncer.ts +3 -2
- package/src/cli/commands/sync-docs/index.ts +73 -100
- package/src/cli/commands/sync-docs/project-reader.ts +17 -18
- package/src/cli/commands/update-user-model.ts +64 -61
- package/src/cli/commands/validate.ts +31 -25
- package/src/cli/session-mining/__tests__/transcript.test.ts +118 -0
- package/src/cli/session-mining/transcript.ts +26 -8
- package/src/context/session-manager.ts +19 -33
- package/src/core/CONTEXT.md +10 -6
- package/src/core/constraints/__tests__/capabilities-reconcile.test.ts +200 -0
- package/src/core/constraints/__tests__/capability-counts.test.ts +94 -0
- package/src/core/constraints/__tests__/git-evidence.test.ts +208 -0
- package/src/core/constraints/__tests__/injection-drift.test.ts +3 -10
- package/src/core/constraints/__tests__/injection-writer.test.ts +231 -0
- package/src/core/constraints/__tests__/trace-injection.test.ts +71 -0
- package/src/core/constraints/__tests__/usage-report.test.ts +112 -0
- package/src/core/constraints/agent-prompt-renderer.ts +2 -6
- package/src/core/constraints/capabilities-parser.ts +53 -35
- package/src/core/constraints/capabilities-reconcile.ts +166 -0
- package/src/core/constraints/checker.ts +82 -133
- package/src/core/constraints/checkers/__tests__/capability-sync.test.ts +273 -0
- package/src/core/constraints/checkers/__tests__/check-outcome.test.ts +176 -0
- package/src/core/constraints/checkers/__tests__/context-doc-sync.test.ts +77 -0
- package/src/core/constraints/checkers/__tests__/docs-freshness.test.ts +126 -0
- package/src/{__tests__ → core/constraints/checkers/__tests__}/governance-presence.test.ts +83 -9
- package/src/core/constraints/checkers/__tests__/iron-flags.test.ts +50 -0
- package/src/core/constraints/checkers/__tests__/no-bypass-checkpoint.test.ts +76 -0
- package/src/{__tests__ → core/constraints/checkers/__tests__}/no-hardcoded-credentials.test.ts +4 -3
- package/src/core/constraints/checkers/__tests__/no-test-simplification.test.ts +58 -0
- package/src/core/constraints/checkers/__tests__/three-state-consistency.test.ts +153 -0
- package/src/core/constraints/checkers/capability-sync.ts +75 -96
- package/src/core/constraints/checkers/context-doc-sync.ts +15 -25
- package/src/core/constraints/checkers/docs-freshness.ts +54 -70
- package/src/core/constraints/checkers/governance-presence.ts +7 -25
- package/src/core/constraints/checkers/index.ts +9 -2
- package/src/core/constraints/checkers/no-test-simplification.ts +4 -3
- package/src/core/constraints/checkers/types.ts +60 -4
- package/src/core/constraints/context-builder.ts +39 -91
- package/src/core/constraints/doc-freshness/runner.ts +2 -1
- package/src/core/constraints/git-evidence.ts +120 -0
- package/src/core/constraints/injection-drift.ts +13 -60
- package/src/core/constraints/injection-writer.ts +212 -0
- package/src/core/constraints/usage-report.ts +36 -17
- package/src/core/index.ts +4 -2
- package/src/core/project-config-loader.ts +49 -9
- package/src/core/validators/__tests__/passes-gate.test.ts +2 -56
- package/src/core/validators/__tests__/test-output.test.ts +372 -0
- package/src/core/validators/passes-gate.ts +86 -248
- package/src/core/validators/test-output.ts +128 -0
- package/src/failure/__tests__/recorder.test.ts +168 -0
- package/src/failure/recorder.ts +12 -10
- package/src/gates/CONTEXT.md +7 -4
- package/src/gates/__tests__/acceptance-types-single-source.test.ts +68 -0
- package/src/gates/__tests__/acceptance.test.ts +4 -86
- package/src/gates/__tests__/checker-gate.test.ts +24 -0
- package/src/gates/__tests__/effective-gates.test.ts +3 -8
- package/src/gates/__tests__/test-verdict-consistency.test.ts +140 -0
- package/src/gates/acceptance.ts +19 -84
- package/src/gates/checker-gate.ts +12 -15
- package/src/gates/command.ts +10 -16
- package/src/gates/contract.ts +22 -61
- package/src/gates/performance.ts +10 -22
- package/src/gates/review.ts +21 -41
- package/src/gates/security.ts +10 -22
- package/src/gates/types.ts +70 -5
- package/src/hooks/CONTEXT.md +1 -1
- package/src/hooks/bootstrap.ts +5 -2
- package/src/index.ts +0 -4
- package/src/knowledge/CONTEXT.md +8 -3
- package/src/knowledge/__tests__/audit-labels.test.ts +44 -0
- package/src/knowledge/__tests__/flywheel-metrics.test.ts +135 -0
- package/src/knowledge/__tests__/import.test.ts +44 -0
- package/src/knowledge/__tests__/index-generator.test.ts +53 -0
- package/src/knowledge/__tests__/ingest.test.ts +85 -0
- package/src/knowledge/__tests__/migration.test.ts +47 -0
- package/src/knowledge/__tests__/reference-tracker.test.ts +16 -0
- package/src/knowledge/__tests__/store.test.ts +194 -0
- package/src/knowledge/audit.ts +67 -71
- package/src/knowledge/flywheel-metrics.ts +71 -0
- package/src/knowledge/import.ts +4 -18
- package/src/knowledge/index-generator.ts +19 -14
- package/src/knowledge/ingest.ts +9 -4
- package/src/knowledge/migration.ts +11 -8
- package/src/knowledge/reference-tracker.ts +12 -8
- package/src/knowledge/store.ts +64 -11
- package/src/monitoring/CONTEXT.md +8 -3
- package/src/monitoring/__tests__/skipped-lines-report.test.ts +178 -0
- package/src/monitoring/__tests__/traces.test.ts +57 -0
- package/src/monitoring/context-tracker.ts +11 -23
- package/src/monitoring/index.ts +1 -1
- package/src/monitoring/trace-analyzer.ts +21 -2
- package/src/monitoring/traces.ts +39 -36
- package/src/release/CONTEXT.md +1 -0
- package/src/release/__tests__/barrel.test.ts +60 -0
- package/src/release/index.ts +2 -13
- package/src/sdd/__tests__/index-generator.test.ts +71 -0
- package/src/sdd/index-generator.ts +9 -9
- package/src/test-setup/__tests__/project-fixture.test.ts +178 -0
- package/src/test-setup/project-fixture.ts +87 -0
- package/src/tools/CONTEXT.md +6 -0
- package/src/tools/__tests__/registry.test.ts +221 -0
- package/src/types/__tests__/types.test.ts +4 -5
- package/src/types/constraint.ts +16 -27
- package/src/types/passes-gate.ts +10 -30
- package/src/types/project-config.ts +1 -1
- package/src/types/session.ts +5 -5
- package/src/types/trace.ts +10 -0
- package/src/utils/__tests__/frontmatter.test.ts +206 -0
- package/src/utils/__tests__/jsonl-skip-disposition.test.ts +175 -0
- package/src/utils/__tests__/jsonl.test.ts +187 -0
- package/src/utils/__tests__/package-version.test.ts +97 -0
- package/src/utils/exec.ts +15 -0
- package/src/utils/file-walk.ts +11 -2
- package/src/utils/frontmatter.ts +121 -0
- package/src/utils/jsonl.ts +167 -0
- package/src/utils/package-version.ts +27 -0
- package/dist/cli/commands/doc-freshness-check.d.ts +0 -53
- package/dist/cli/commands/doc-freshness-check.d.ts.map +0 -1
- package/dist/cli/commands/doc-freshness-check.js +0 -352
- package/dist/cli/commands/doc-freshness-check.js.map +0 -1
- package/dist/types/index.d.ts +0 -14
- package/dist/types/index.d.ts.map +0 -1
- package/dist/types/index.js +0 -39
- package/dist/types/index.js.map +0 -1
- package/src/__tests__/long-running.test.ts +0 -17
- package/src/__tests__/passes-gate-extension.test.ts +0 -151
- package/src/cli/commands/__tests__/doc-freshness-check.test.ts +0 -168
- package/src/cli/commands/doc-freshness-check.ts +0 -386
- package/src/spec/CONTEXT.md +0 -11
- package/src/types/index.ts +0 -47
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
* harness constraints retire —— 约束退役(ADR-0001 决策 2/5)
|
|
3
3
|
*
|
|
4
4
|
* 建议层全自动(候选诊断复用 report 数据层),执行层保留一次人确认。
|
|
5
|
-
*
|
|
5
|
+
* 落盘形态(studio#82 D6 一处真相):
|
|
6
6
|
*
|
|
7
7
|
* - 内置约束 → config.yml `enabled: false` + `retired` 元数据:
|
|
8
8
|
*
|
|
@@ -33,21 +33,24 @@
|
|
|
33
33
|
import * as fs from 'fs';
|
|
34
34
|
import * as path from 'path';
|
|
35
35
|
import * as readline from 'readline';
|
|
36
|
+
import { log, logError, processIO, type CommandIO, type CommandResult } from '../command-contract';
|
|
36
37
|
import * as yaml from 'js-yaml';
|
|
37
38
|
import chalk from 'chalk';
|
|
38
39
|
import { getConstraint } from '../../core/constraints/definitions';
|
|
39
|
-
import { renderConstraintsSection, CONSTRAINTS_END_MARKER } from '../../core/constraints/injection-renderer';
|
|
40
|
-
import { resolveInjectionTarget } from '../../core/constraints/injection-
|
|
40
|
+
import { renderConstraintsSection, CONSTRAINTS_START_MARKER, CONSTRAINTS_END_MARKER } from '../../core/constraints/injection-renderer';
|
|
41
|
+
import { replaceStandaloneRange, resolveInjectionTarget } from '../../core/constraints/injection-writer';
|
|
41
42
|
import { getEffectiveConstraints } from '../../core/effective-constraints';
|
|
42
43
|
import { loadRawProjectConfig, ProjectConfigLoader } from '../../core/project-config-loader';
|
|
44
|
+
import { getHarnessPackageVersion } from '../../utils/package-version';
|
|
43
45
|
import { FileKnowledgeStore } from '../../knowledge/store';
|
|
44
46
|
import type { KnowledgeEntry } from '../../knowledge/types';
|
|
45
47
|
import type { Constraint } from '../../types/constraint';
|
|
46
48
|
import {
|
|
47
49
|
buildConstraintsUsageReport,
|
|
50
|
+
CANDIDATE_KIND_LABEL,
|
|
48
51
|
collectUsageByConstraint,
|
|
49
52
|
readProjectTraces,
|
|
50
|
-
|
|
53
|
+
readProjectTracesReport,
|
|
51
54
|
} from '../../core/constraints/usage-report';
|
|
52
55
|
|
|
53
56
|
export interface RetireExecuteOptions {
|
|
@@ -64,7 +67,7 @@ export interface RetireResult {
|
|
|
64
67
|
status: RetireStatus;
|
|
65
68
|
/** 是否 check 层 iron(交互模式据此追加确认) */
|
|
66
69
|
isIronLaw: boolean;
|
|
67
|
-
/** 退役落点:custom 约束落 custom-constraints.yml
|
|
70
|
+
/** 退役落点:custom 约束落 custom-constraints.yml(studio#82 D6),内置落 config.yml */
|
|
68
71
|
landing: 'config.yml' | 'custom-constraints.yml';
|
|
69
72
|
stats: { total: number; fail: number; failRate: number };
|
|
70
73
|
/** 治理注入段(CLAUDE.md / AGENTS.md)是否已同步 */
|
|
@@ -128,18 +131,6 @@ function findRetireTarget(projectRoot: string, id: string): RetireTargetInfo | u
|
|
|
128
131
|
return undefined;
|
|
129
132
|
}
|
|
130
133
|
|
|
131
|
-
/**
|
|
132
|
-
* 读取 harness 版本(与 init.ts 同路径策略)
|
|
133
|
-
*/
|
|
134
|
-
function getHarnessVersion(): string {
|
|
135
|
-
try {
|
|
136
|
-
const pkgPath = path.join(__dirname, '..', '..', '..', 'package.json');
|
|
137
|
-
return JSON.parse(fs.readFileSync(pkgPath, 'utf-8')).version ?? 'unknown';
|
|
138
|
-
} catch {
|
|
139
|
-
return 'unknown';
|
|
140
|
-
}
|
|
141
|
-
}
|
|
142
|
-
|
|
143
134
|
/**
|
|
144
135
|
* 写 config.yml 退役段(ADR-0001 决策 5)
|
|
145
136
|
*
|
|
@@ -174,7 +165,7 @@ function writeRetireConfig(
|
|
|
174
165
|
}
|
|
175
166
|
|
|
176
167
|
/**
|
|
177
|
-
* 写 custom-constraints.yml
|
|
168
|
+
* 写 custom-constraints.yml 退役段(studio#82 D6 统一落点)
|
|
178
169
|
*
|
|
179
170
|
* 在 custom_constraints.<id> 条目内追加 retired 元数据,保留规则原文。
|
|
180
171
|
* js-yaml 不保留注释:原文件含注释行时重写会丢失,console 说明。
|
|
@@ -280,12 +271,10 @@ function syncGovernanceInjection(projectRoot: string): { synced: boolean; file?:
|
|
|
280
271
|
const target = resolveInjectionTarget(projectRoot);
|
|
281
272
|
if (!target) return { synced: false };
|
|
282
273
|
|
|
283
|
-
const
|
|
284
|
-
const
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
if (newContent !== target.content) {
|
|
288
|
-
fs.writeFileSync(filePath, newContent, 'utf-8');
|
|
274
|
+
const body = renderConstraintsSection(getEffectiveConstraints(projectRoot), getHarnessPackageVersion());
|
|
275
|
+
const write = replaceStandaloneRange(target.content, CONSTRAINTS_START_MARKER, CONSTRAINTS_END_MARKER, body);
|
|
276
|
+
if (write.kind === 'updated' && write.content !== target.content) {
|
|
277
|
+
fs.writeFileSync(path.join(projectRoot, target.file), write.content, 'utf-8');
|
|
289
278
|
}
|
|
290
279
|
return { synced: true, file: target.file };
|
|
291
280
|
}
|
|
@@ -327,6 +316,9 @@ export function retireConstraint(
|
|
|
327
316
|
}
|
|
328
317
|
|
|
329
318
|
// 历史统计(来自 traces.log)
|
|
319
|
+
// 计数去向:兼容包装 readProjectTraces() 丢计数(harness#100)——落盘的 retire stats 只计
|
|
320
|
+
// 合法记录,把坏行数写进 RetireResult.stats 属形状变更不在本票;本函数按契约「纯执行无交互」
|
|
321
|
+
// 不打印,告知由两条命令入口各自负责(runRetireInteractive 顶部 / constraintsRetire 的 --yes 分支)
|
|
330
322
|
const usage = collectUsageByConstraint(readProjectTraces(projectRoot)).get(id);
|
|
331
323
|
const evaluated = usage ? usage.total - usage.skip : 0;
|
|
332
324
|
const stats = {
|
|
@@ -366,29 +358,30 @@ export function retireConstraint(
|
|
|
366
358
|
/**
|
|
367
359
|
* 打印单条退役结果(含回滚语义提示)
|
|
368
360
|
*/
|
|
369
|
-
export function printRetireResult(result: RetireResult):
|
|
361
|
+
export function printRetireResult(result: RetireResult, io: CommandIO = processIO): CommandResult {
|
|
370
362
|
switch (result.status) {
|
|
371
363
|
case 'unknown_id':
|
|
372
|
-
|
|
373
|
-
return;
|
|
364
|
+
log(io, chalk.red(`❌ ${result.id}: 约束不存在(既非内置也非 custom-constraints),未做任何变更`));
|
|
365
|
+
return { kind: 'skip', reason: `${result.id}: 约束不存在,未做任何变更` };
|
|
374
366
|
case 'already_retired':
|
|
375
|
-
|
|
376
|
-
return;
|
|
367
|
+
log(io, chalk.yellow(`⚠️ ${result.id}: 已处于退役状态(config.yml 中 enabled: false),跳过`));
|
|
368
|
+
return { kind: 'skip', reason: `${result.id}: 已处于退役状态,跳过` };
|
|
377
369
|
case 'retired': {
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
370
|
+
log(io, chalk.green(`✅ ${result.id}: 已退役`));
|
|
371
|
+
log(io, ` 历史统计: total=${result.stats.total} fail=${result.stats.fail} fail率=${Math.round(result.stats.failRate * 100)}%`);
|
|
372
|
+
log(io, ` 知识沉淀: ${result.knowledgeEntryId}(.harness/knowledge)`);
|
|
381
373
|
if (result.injectionSynced) {
|
|
382
|
-
|
|
374
|
+
log(io, ` 已同步 ${result.injectionFile ?? '治理文档'} 注入段`);
|
|
383
375
|
}
|
|
384
376
|
const recovery =
|
|
385
377
|
result.landing === 'custom-constraints.yml'
|
|
386
378
|
? `删除 custom-constraints.yml 中 custom_constraints.${result.id}.retired 段`
|
|
387
379
|
: `删除 config.yml 中 constraints.${result.id} 段`;
|
|
388
|
-
|
|
380
|
+
log(io, chalk.gray(` retire 不是删除——恢复方法:${recovery}`));
|
|
389
381
|
break;
|
|
390
382
|
}
|
|
391
383
|
}
|
|
384
|
+
return { kind: 'ok' };
|
|
392
385
|
}
|
|
393
386
|
|
|
394
387
|
// ========================================
|
|
@@ -408,13 +401,6 @@ function createAsk(io: RetireIO): { ask: (q: string) => Promise<string>; close:
|
|
|
408
401
|
};
|
|
409
402
|
}
|
|
410
403
|
|
|
411
|
-
const CANDIDATE_KIND_LABEL: Record<RetireCandidate['kind'], string> = {
|
|
412
|
-
zero_trigger: '零触发',
|
|
413
|
-
unevaluable: '不可评估',
|
|
414
|
-
high_noise: '高噪',
|
|
415
|
-
zero_intercept: '零拦截',
|
|
416
|
-
};
|
|
417
|
-
|
|
418
404
|
/**
|
|
419
405
|
* 交互式退役(候选列表 → 编号多选 → 摘要 → 确认 → 执行)
|
|
420
406
|
*
|
|
@@ -423,9 +409,16 @@ const CANDIDATE_KIND_LABEL: Record<RetireCandidate['kind'], string> = {
|
|
|
423
409
|
export async function runRetireInteractive(
|
|
424
410
|
projectRoot: string,
|
|
425
411
|
io: RetireIO = { input: process.stdin, output: process.stdout }
|
|
426
|
-
): Promise<
|
|
412
|
+
): Promise<CommandResult> {
|
|
427
413
|
const report = buildConstraintsUsageReport(projectRoot);
|
|
414
|
+
// 候选诊断是退役决策的依据:数据不完整必须先说(harness#100,与 report 同一降级维度);
|
|
415
|
+
// 告知行走 stderr,与 status / failure list / 直达分支同一去向(交互正文仍走 console.log)
|
|
416
|
+
if (report.skippedLines > 0) {
|
|
417
|
+
console.error(chalk.yellow(`⚠️ trace 文件有 ${report.skippedLines} 行损坏已跳过,候选只基于其余合法记录`));
|
|
418
|
+
}
|
|
428
419
|
const { ask, close } = createAsk(io);
|
|
420
|
+
// 退役结果打印走注入流(与 readline 提示同一去向)
|
|
421
|
+
const out = { stdout: io.output, stderr: io.output } as unknown as CommandIO;
|
|
429
422
|
|
|
430
423
|
try {
|
|
431
424
|
let selectedIds: string[] = [];
|
|
@@ -435,7 +428,7 @@ export async function runRetireInteractive(
|
|
|
435
428
|
const manual = await ask('可手动输入要退役的约束 id(留空取消): ');
|
|
436
429
|
if (!manual) {
|
|
437
430
|
console.log('已取消');
|
|
438
|
-
return;
|
|
431
|
+
return { kind: 'skip', reason: '交互未确认,未做任何变更' };
|
|
439
432
|
}
|
|
440
433
|
selectedIds = [manual];
|
|
441
434
|
} else {
|
|
@@ -447,7 +440,7 @@ export async function runRetireInteractive(
|
|
|
447
440
|
const answer = await ask('输入编号(逗号分隔多选)或约束 id,留空取消: ');
|
|
448
441
|
if (!answer) {
|
|
449
442
|
console.log('已取消');
|
|
450
|
-
return;
|
|
443
|
+
return { kind: 'skip', reason: '交互未确认,未做任何变更' };
|
|
451
444
|
}
|
|
452
445
|
|
|
453
446
|
for (const token of answer.split(',').map(s => s.trim()).filter(Boolean)) {
|
|
@@ -482,7 +475,7 @@ export async function runRetireInteractive(
|
|
|
482
475
|
|
|
483
476
|
if (plan.length === 0) {
|
|
484
477
|
console.log('无可执行项,已取消');
|
|
485
|
-
return;
|
|
478
|
+
return { kind: 'skip', reason: '交互未确认,未做任何变更' };
|
|
486
479
|
}
|
|
487
480
|
|
|
488
481
|
// 变更摘要 → 最终确认
|
|
@@ -500,17 +493,18 @@ export async function runRetireInteractive(
|
|
|
500
493
|
const finalConfirm = await ask('确认执行?(y/N) ');
|
|
501
494
|
if (finalConfirm.toLowerCase() !== 'y' && finalConfirm.toLowerCase() !== 'yes') {
|
|
502
495
|
console.log('已取消');
|
|
503
|
-
return;
|
|
496
|
+
return { kind: 'skip', reason: '交互未确认,未做任何变更' };
|
|
504
497
|
}
|
|
505
498
|
|
|
506
499
|
console.log();
|
|
507
500
|
for (const p of plan) {
|
|
508
501
|
const result = retireConstraint(projectRoot, p.id, { reason: p.reason });
|
|
509
|
-
printRetireResult(result);
|
|
502
|
+
printRetireResult(result, out);
|
|
510
503
|
}
|
|
511
504
|
} finally {
|
|
512
505
|
close();
|
|
513
506
|
}
|
|
507
|
+
return { kind: 'ok' };
|
|
514
508
|
}
|
|
515
509
|
|
|
516
510
|
/**
|
|
@@ -519,29 +513,38 @@ export async function runRetireInteractive(
|
|
|
519
513
|
* 人确认闸门(#24,ADR-0001 决策 2):带 id 的直达路径必须显式 `--yes`,
|
|
520
514
|
* 无 `--yes` 报错 + 非零退出码,提示改用 `--yes` 或交互模式;不落盘任何文件。
|
|
521
515
|
*/
|
|
522
|
-
export async function constraintsRetire(
|
|
516
|
+
export async function constraintsRetire(
|
|
517
|
+
id?: string,
|
|
518
|
+
options: ConstraintsRetireOptions = {},
|
|
519
|
+
io: CommandIO = processIO,
|
|
520
|
+
): Promise<CommandResult> {
|
|
523
521
|
const projectRoot = options.projectPath || process.cwd();
|
|
524
522
|
|
|
525
523
|
if (id) {
|
|
526
524
|
// 非交互直达:执行层人确认对所有入口成立(含程序化调用方)
|
|
527
525
|
if (!options.yes) {
|
|
528
|
-
|
|
526
|
+
logError(io,
|
|
529
527
|
chalk.red(`❌ 直达退役需要显式人确认(ADR-0001 决策 2:执行层保留一次人确认),未做任何变更\n`) +
|
|
530
528
|
` 带 --yes 显式确认直达:harness constraints retire ${id} --yes` +
|
|
531
529
|
`${options.reason ? ` --reason "${options.reason}"` : ''}\n` +
|
|
532
530
|
` 或去掉 id 走交互确认:harness constraints retire`
|
|
533
531
|
);
|
|
534
|
-
|
|
535
|
-
|
|
532
|
+
return { kind: 'usage-error', reason: `直达退役 ${id} 缺少显式 --yes 人确认,未做任何变更` };
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
// 落盘的 retire stats 只含合法记录:依据不完整要在执行前告知(harness#100,
|
|
536
|
+
// 直达路径不经过 runRetireInteractive,故两处各自告知)
|
|
537
|
+
const { skippedLines } = readProjectTracesReport(projectRoot);
|
|
538
|
+
if (skippedLines > 0) {
|
|
539
|
+
logError(io, chalk.yellow(`⚠️ trace 文件有 ${skippedLines} 行损坏已跳过,落盘的退役统计只基于其余合法记录`));
|
|
536
540
|
}
|
|
537
541
|
|
|
538
542
|
const result = retireConstraint(projectRoot, id, { reason: options.reason });
|
|
539
543
|
if (result.status === 'retired' && result.isIronLaw) {
|
|
540
|
-
|
|
544
|
+
log(io, chalk.yellow(`⚠️ ${id} 是一条 Iron Law,已通过 --yes 直达退役(交互模式会要求二次确认)`));
|
|
541
545
|
}
|
|
542
|
-
printRetireResult(result);
|
|
543
|
-
return;
|
|
546
|
+
return printRetireResult(result, io);
|
|
544
547
|
}
|
|
545
548
|
|
|
546
|
-
|
|
549
|
+
return runRetireInteractive(projectRoot);
|
|
547
550
|
}
|
|
@@ -5,10 +5,10 @@
|
|
|
5
5
|
* 供 Studio 等消费者获取约束的 hash、计数、文本大小等元数据。
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
-
import { readFileSync, existsSync } from 'fs';
|
|
9
|
-
import { join } from 'path';
|
|
10
8
|
import { createHash } from 'crypto';
|
|
11
9
|
import { getAllConstraints } from '../../core/constraints/definitions';
|
|
10
|
+
import { getHarnessPackageVersion } from '../../utils/package-version';
|
|
11
|
+
import { log, processIO, type CommandIO, type CommandResult } from '../command-contract';
|
|
12
12
|
|
|
13
13
|
export interface ConstraintsMeta {
|
|
14
14
|
version: string;
|
|
@@ -17,24 +17,6 @@ export interface ConstraintsMeta {
|
|
|
17
17
|
textSize: { total: number; perConstraint: number };
|
|
18
18
|
}
|
|
19
19
|
|
|
20
|
-
function getPackageVersion(): string {
|
|
21
|
-
// Try several common locations
|
|
22
|
-
const candidates = [
|
|
23
|
-
join(__dirname, '..', '..', '..', 'package.json'),
|
|
24
|
-
join(process.cwd(), 'package.json'),
|
|
25
|
-
];
|
|
26
|
-
for (const p of candidates) {
|
|
27
|
-
if (existsSync(p)) {
|
|
28
|
-
try {
|
|
29
|
-
return JSON.parse(readFileSync(p, 'utf-8')).version;
|
|
30
|
-
} catch {
|
|
31
|
-
// continue to next candidate
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
return 'unknown';
|
|
36
|
-
}
|
|
37
|
-
|
|
38
20
|
export function getConstraintsMeta(): ConstraintsMeta {
|
|
39
21
|
const constraints = getAllConstraints();
|
|
40
22
|
|
|
@@ -56,7 +38,7 @@ export function getConstraintsMeta(): ConstraintsMeta {
|
|
|
56
38
|
const hash = createHash('sha256').update(hashInput).digest('hex');
|
|
57
39
|
|
|
58
40
|
return {
|
|
59
|
-
version:
|
|
41
|
+
version: getHarnessPackageVersion(),
|
|
60
42
|
hash,
|
|
61
43
|
counts: {
|
|
62
44
|
ironLaws: ironLaws.length,
|
|
@@ -73,14 +55,15 @@ export function getConstraintsMeta(): ConstraintsMeta {
|
|
|
73
55
|
/**
|
|
74
56
|
* CLI handler: output --json
|
|
75
57
|
*/
|
|
76
|
-
export async function constraints(options: { json?: boolean }): Promise<
|
|
58
|
+
export async function constraints(options: { json?: boolean }, io: CommandIO = processIO): Promise<CommandResult> {
|
|
77
59
|
const meta = getConstraintsMeta();
|
|
78
60
|
if (options.json) {
|
|
79
|
-
|
|
61
|
+
log(io, JSON.stringify(meta, null, 2));
|
|
80
62
|
} else {
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
63
|
+
log(io, `version: ${meta.version}`);
|
|
64
|
+
log(io, `hash: ${meta.hash}`);
|
|
65
|
+
log(io, `ironLaws: ${meta.counts.ironLaws}, guidelines: ${meta.counts.guidelines}, prompts: ${meta.counts.prompts}`);
|
|
66
|
+
log(io, `textSize: ${meta.textSize.total} chars total, ~${meta.textSize.perConstraint} chars/constraint`);
|
|
85
67
|
}
|
|
68
|
+
return { kind: 'ok' };
|
|
86
69
|
}
|
|
@@ -8,6 +8,7 @@ import chalk from 'chalk';
|
|
|
8
8
|
import * as fs from 'fs/promises';
|
|
9
9
|
import * as path from 'path';
|
|
10
10
|
import { ContractGate } from '../../gates/contract';
|
|
11
|
+
import { log, processIO, type CommandIO, type CommandResult } from '../command-contract';
|
|
11
12
|
|
|
12
13
|
export interface ContractOptions {
|
|
13
14
|
/** 项目路径 */
|
|
@@ -23,8 +24,11 @@ export interface ContractOptions {
|
|
|
23
24
|
/**
|
|
24
25
|
* 执行契约门控
|
|
25
26
|
*/
|
|
26
|
-
export async function contract(
|
|
27
|
-
|
|
27
|
+
export async function contract(
|
|
28
|
+
options: ContractOptions,
|
|
29
|
+
io: CommandIO = processIO,
|
|
30
|
+
): Promise<CommandResult> {
|
|
31
|
+
log(io, chalk.blue('📜 API 契约门控检查...'));
|
|
28
32
|
|
|
29
33
|
const projectPath = options.projectPath || process.cwd();
|
|
30
34
|
const contractPath = options.contractPath || 'openapi.yaml';
|
|
@@ -34,10 +38,10 @@ export async function contract(options: ContractOptions): Promise<void> {
|
|
|
34
38
|
try {
|
|
35
39
|
await fs.access(fullPath);
|
|
36
40
|
} catch {
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
+
log(io);
|
|
42
|
+
log(io, chalk.red('❌ 契约文件不存在'));
|
|
43
|
+
log(io, chalk.red(` ${fullPath}`));
|
|
44
|
+
return { kind: 'fail', reason: `contract file not found: ${fullPath}` };
|
|
41
45
|
}
|
|
42
46
|
|
|
43
47
|
// 创建契约门控实例
|
|
@@ -53,57 +57,61 @@ export async function contract(options: ContractOptions): Promise<void> {
|
|
|
53
57
|
} as any);
|
|
54
58
|
|
|
55
59
|
if (result.passed) {
|
|
56
|
-
|
|
57
|
-
|
|
60
|
+
log(io);
|
|
61
|
+
log(io, chalk.green('✅ 契约门控检查通过'));
|
|
58
62
|
|
|
59
63
|
if (result.details) {
|
|
60
|
-
|
|
64
|
+
log(io, chalk.gray(` Schema 有效: ✅`));
|
|
61
65
|
if (result.details.endpoints) {
|
|
62
|
-
|
|
66
|
+
log(io, chalk.gray(` 端点数: ${result.details.endpoints}`));
|
|
63
67
|
}
|
|
64
68
|
if (result.details.breakingChanges === false) {
|
|
65
|
-
|
|
69
|
+
log(io, chalk.gray(` 破坏性变更: 无`));
|
|
66
70
|
}
|
|
67
71
|
}
|
|
68
72
|
} else {
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
73
|
+
log(io);
|
|
74
|
+
log(io, chalk.red('❌ 契约门控检查失败'));
|
|
75
|
+
log(io, chalk.red(` ${result.message}`));
|
|
72
76
|
|
|
73
77
|
if (result.details?.errors) {
|
|
74
|
-
|
|
75
|
-
|
|
78
|
+
log(io);
|
|
79
|
+
log(io, chalk.red('验证错误:'));
|
|
76
80
|
(result.details.errors as string[]).forEach((error: string) => {
|
|
77
|
-
|
|
81
|
+
log(io, chalk.red(` - ${error}`));
|
|
78
82
|
});
|
|
79
83
|
}
|
|
80
84
|
|
|
81
85
|
if (result.details?.breakingChanges) {
|
|
82
|
-
|
|
83
|
-
|
|
86
|
+
log(io);
|
|
87
|
+
log(io, chalk.red('破坏性变更:'));
|
|
84
88
|
(result.details.breakingChanges as any[]).forEach((change: any) => {
|
|
85
|
-
|
|
89
|
+
log(io, chalk.red(` - ${change.type}: ${change.path}`));
|
|
86
90
|
if (change.description) {
|
|
87
|
-
|
|
91
|
+
log(io, chalk.gray(` ${change.description}`));
|
|
88
92
|
}
|
|
89
93
|
});
|
|
90
94
|
}
|
|
91
95
|
|
|
92
|
-
|
|
96
|
+
return { kind: 'fail', reason: `contract gate denied: ${result.message}` };
|
|
93
97
|
}
|
|
98
|
+
return { kind: 'ok' };
|
|
94
99
|
} catch (error: any) {
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
100
|
+
log(io);
|
|
101
|
+
log(io, chalk.red('❌ 契约门控检查出错'));
|
|
102
|
+
log(io, chalk.red(` ${error.message}`));
|
|
103
|
+
return { kind: 'fail', reason: `contract gate error: ${error.message}` };
|
|
99
104
|
}
|
|
100
105
|
}
|
|
101
106
|
|
|
102
107
|
/**
|
|
103
108
|
* 验证 OpenAPI Schema 语法
|
|
104
109
|
*/
|
|
105
|
-
export async function validateSchema(
|
|
106
|
-
|
|
110
|
+
export async function validateSchema(
|
|
111
|
+
options: ContractOptions,
|
|
112
|
+
io: CommandIO = processIO,
|
|
113
|
+
): Promise<CommandResult> {
|
|
114
|
+
log(io, chalk.blue('📜 验证 OpenAPI Schema...\n'));
|
|
107
115
|
|
|
108
116
|
const projectPath = options.projectPath || process.cwd();
|
|
109
117
|
const contractPath = options.contractPath || 'openapi.yaml';
|
|
@@ -118,8 +126,8 @@ export async function validateSchema(options: ContractOptions): Promise<void> {
|
|
|
118
126
|
try {
|
|
119
127
|
schema = yaml.load(content);
|
|
120
128
|
} catch (e: any) {
|
|
121
|
-
|
|
122
|
-
|
|
129
|
+
log(io, chalk.red(`❌ YAML 解析错误: ${e.message}`));
|
|
130
|
+
return { kind: 'fail', reason: `contract YAML parse error: ${e.message}` };
|
|
123
131
|
}
|
|
124
132
|
|
|
125
133
|
// 基本验证
|
|
@@ -143,26 +151,27 @@ export async function validateSchema(options: ContractOptions): Promise<void> {
|
|
|
143
151
|
}
|
|
144
152
|
|
|
145
153
|
if (errors.length > 0) {
|
|
146
|
-
|
|
147
|
-
errors.forEach(err =>
|
|
148
|
-
|
|
154
|
+
log(io, chalk.red('❌ Schema 验证失败:\n'));
|
|
155
|
+
errors.forEach(err => log(io, chalk.red(` - ${err}`)));
|
|
156
|
+
return { kind: 'fail', reason: `contract schema invalid: ${errors.join('; ')}` };
|
|
149
157
|
}
|
|
150
158
|
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
159
|
+
log(io, chalk.green('✅ Schema 验证通过'));
|
|
160
|
+
log(io);
|
|
161
|
+
log(io, chalk.gray('Schema 信息:'));
|
|
162
|
+
log(io, chalk.gray(` 版本: ${schema.openapi}`));
|
|
163
|
+
log(io, chalk.gray(` 标题: ${schema.info.title}`));
|
|
164
|
+
log(io, chalk.gray(` API 版本: ${schema.info.version}`));
|
|
157
165
|
|
|
158
166
|
if (schema.paths) {
|
|
159
167
|
const endpoints = Object.keys(schema.paths).flatMap(path =>
|
|
160
168
|
Object.keys(schema.paths[path]).map(method => `${method.toUpperCase()} ${path}`)
|
|
161
169
|
);
|
|
162
|
-
|
|
170
|
+
log(io, chalk.gray(` 端点数: ${endpoints.length}`));
|
|
163
171
|
}
|
|
172
|
+
return { kind: 'ok' };
|
|
164
173
|
} catch (error: any) {
|
|
165
|
-
|
|
166
|
-
|
|
174
|
+
log(io, chalk.red(`❌ 验证失败: ${error.message}`));
|
|
175
|
+
return { kind: 'fail', reason: `contract schema read error: ${error.message}` };
|
|
167
176
|
}
|
|
168
177
|
}
|