@danmoisan/drm-copilot-mcp 1.1.17 → 1.1.19
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/out/mcp-server.js +1405 -684
- package/package.json +6 -4
- package/resources/claude-customizations/.claude/agents/atomic-executor.md +11 -0
- package/resources/claude-customizations/.claude/agents/atomic-planner.md +10 -0
- package/resources/claude-customizations/.claude/agents/epic-orchestrator.md +12 -4
- package/resources/claude-customizations/.claude/agents/epic-planner.md +5 -4
- package/resources/claude-customizations/.claude/agents/feature-review.md +16 -5
- package/resources/claude-customizations/.claude/agents/orchestrator.md +21 -7
- package/resources/claude-customizations/.claude/agents/parallel-orchestrator.md +37 -13
- package/resources/claude-customizations/.claude/agents/parallel-planner.md +9 -6
- package/resources/claude-customizations/.claude/agents/pr-author.md +15 -2
- package/resources/claude-customizations/.claude/agents/prd-feature.md +1 -1
- package/resources/claude-customizations/.claude/hooks/check-powershell-test-purity.ps1 +7 -1
- package/resources/claude-customizations/.claude/hooks/check-python-test-purity.ps1 +7 -1
- package/resources/claude-customizations/.claude/hooks/enforce-checkpoint-monotonic.ps1 +7 -1
- package/resources/claude-customizations/.claude/hooks/enforce-completion-consistency.ps1 +111 -46
- package/resources/claude-customizations/.claude/hooks/enforce-completion-helpers.ps1 +105 -0
- package/resources/claude-customizations/.claude/hooks/enforce-discovery-artifact-gate.ps1 +8 -1
- package/resources/claude-customizations/.claude/hooks/enforce-epic-invocation-origin.ps1 +7 -1
- package/resources/claude-customizations/.claude/hooks/enforce-epic-merge-gate-resolution.ps1 +116 -59
- package/resources/claude-customizations/.claude/hooks/enforce-epic-merge-gate.ps1 +55 -23
- package/resources/claude-customizations/.claude/hooks/enforce-epic-wave-barrier.ps1 +74 -75
- package/resources/claude-customizations/.claude/hooks/enforce-epic-worktree-removal-gate-resolution.ps1 +127 -35
- package/resources/claude-customizations/.claude/hooks/enforce-epic-worktree-removal-gate.ps1 +61 -57
- package/resources/claude-customizations/.claude/hooks/enforce-evidence-locations.ps1 +7 -1
- package/resources/claude-customizations/.claude/hooks/enforce-feature-folder-order.ps1 +129 -39
- package/resources/claude-customizations/.claude/hooks/enforce-mermaid-validation.ps1 +7 -1
- package/resources/claude-customizations/.claude/hooks/enforce-model-routing-receipt.ps1 +9 -3
- package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate-epic-scope.ps1 +39 -51
- package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate-helpers.ps1 +31 -58
- package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate-modes.ps1 +63 -47
- package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate-targets.ps1 +433 -0
- package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate.ps1 +17 -12
- package/resources/claude-customizations/.claude/hooks/enforce-parallel-abandon-gate.ps1 +9 -3
- package/resources/claude-customizations/.claude/hooks/enforce-parallel-cohort-barrier.ps1 +65 -50
- package/resources/claude-customizations/.claude/hooks/enforce-parallel-drift-gate.ps1 +49 -42
- package/resources/claude-customizations/.claude/hooks/enforce-parallel-worktree-removal-gate.ps1 +54 -72
- package/resources/claude-customizations/.claude/hooks/enforce-powershell-batch-budget.ps1 +8 -2
- package/resources/claude-customizations/.claude/hooks/enforce-pr-author-command-allowlist.ps1 +279 -0
- package/resources/claude-customizations/.claude/hooks/enforce-pr-author-skill-helpers.ps1 +129 -75
- package/resources/claude-customizations/.claude/hooks/enforce-pr-author-skill.artifact-root.ps1 +233 -0
- package/resources/claude-customizations/.claude/hooks/enforce-pr-author-skill.docs-only.ps1 +224 -0
- package/resources/claude-customizations/.claude/hooks/enforce-pr-author-skill.ps1 +69 -24
- package/resources/claude-customizations/.claude/hooks/enforce-prd-feature-before-planner-helpers.ps1 +29 -18
- package/resources/claude-customizations/.claude/hooks/enforce-prd-feature-before-planner.ps1 +10 -4
- package/resources/claude-customizations/.claude/hooks/enforce-promotion-mcp-only.ps1 +14 -5
- package/resources/claude-customizations/.claude/hooks/enforce-python-batch-budget.ps1 +8 -2
- package/resources/claude-customizations/.claude/hooks/feature-folder-resolution.ps1 +373 -0
- package/resources/claude-customizations/.claude/hooks/feature-review-coverage-thresholds.ps1 +85 -0
- package/resources/claude-customizations/.claude/hooks/hook-command-heredoc.ps1 +119 -0
- package/resources/claude-customizations/.claude/hooks/hook-command-invocation-operands.ps1 +198 -0
- package/resources/claude-customizations/.claude/hooks/hook-command-invocation.ps1 +254 -255
- package/resources/claude-customizations/.claude/hooks/hook-command-payload-powershell.ps1 +201 -0
- package/resources/claude-customizations/.claude/hooks/hook-command-payload.ps1 +484 -0
- package/resources/claude-customizations/.claude/hooks/hook-command-scanner.ps1 +27 -110
- package/resources/claude-customizations/.claude/hooks/hook-dependency-guard.ps1 +114 -0
- package/resources/claude-customizations/.claude/hooks/hook-docs-only-diff.ps1 +493 -0
- package/resources/claude-customizations/.claude/hooks/subagentstop-envelope.ps1 +192 -0
- package/resources/claude-customizations/.claude/hooks/validate-bash.ps1 +9 -3
- package/resources/claude-customizations/.claude/hooks/validate-discovery-artifact-gate.ps1 +40 -42
- package/resources/claude-customizations/.claude/hooks/validate-executor-output.ps1 +66 -38
- package/resources/claude-customizations/.claude/hooks/validate-feature-review-coverage-metrics.ps1 +180 -0
- package/resources/claude-customizations/.claude/hooks/validate-feature-review-coverage-rules.ps1 +195 -0
- package/resources/claude-customizations/.claude/hooks/validate-feature-review-coverage.ps1 +141 -395
- package/resources/claude-customizations/.claude/hooks/validate-orchestrator-output-resolution.ps1 +311 -0
- package/resources/claude-customizations/.claude/hooks/validate-orchestrator-output-routing.ps1 +170 -0
- package/resources/claude-customizations/.claude/hooks/validate-orchestrator-output.ps1 +115 -190
- package/resources/claude-customizations/.claude/hooks/validate-planner-output.ps1 +64 -32
- package/resources/claude-customizations/.claude/hooks/validate-pr-author-output.ps1 +39 -44
- package/resources/claude-customizations/.claude/hooks/validate-prd-feature-output.ps1 +43 -14
- package/resources/claude-customizations/.claude/hooks/validate-required-artifact-output.ps1 +66 -36
- package/resources/claude-customizations/.claude/hooks/validate-task-researcher-output.ps1 +31 -34
- package/resources/claude-customizations/.claude/lib/bash/mutate-parallel-run.sh +191 -0
- package/resources/claude-customizations/.claude/lib/bash/parallel-cohorts.sh +13 -3
- package/resources/claude-customizations/.claude/lib/bash/parallel-lane-assertion.sh +4 -2
- package/resources/claude-customizations/.claude/lib/bash/parallel-mutation-cli.sh +152 -0
- package/resources/claude-customizations/.claude/lib/bash/parallel-mutation-ops.sh +193 -0
- package/resources/claude-customizations/.claude/lib/bash/parallel-mutation.sh +322 -0
- package/resources/claude-customizations/.claude/lib/bash/remove-parallel-item.sh +146 -0
- package/resources/claude-customizations/.claude/lib/blast-radius/BlastRadiusExtraction.psm1 +23 -33
- package/resources/claude-customizations/.claude/lib/blast-radius/BlastRadiusTokenShape.psm1 +86 -6
- package/resources/claude-customizations/.claude/lib/ci-gate/Invoke-CiGateParser.ps1 +91 -19
- package/resources/claude-customizations/.claude/lib/orchestrator-state/OrchestratorState.psm1 +6 -13
- package/resources/claude-customizations/.claude/lib/orchestrator-state/OrchestratorStateEpicWaveBarrier.psm1 +346 -0
- package/resources/claude-customizations/.claude/lib/orchestrator-state/OrchestratorStateIssueAdoption.psm1 +396 -0
- package/resources/claude-customizations/.claude/lib/orchestrator-state/OrchestratorStateReceipts.psm1 +22 -15
- package/resources/claude-customizations/.claude/lib/orchestrator-state/OrchestratorStateRemediationAccounting.psm1 +337 -0
- package/resources/claude-customizations/.claude/lib/orchestrator-state/OrchestratorStateRoutingContract.psm1 +9 -1
- package/resources/claude-customizations/.claude/lib/worktree-resolution/WorktreeItemResolution.psm1 +79 -2
- package/resources/claude-customizations/.claude/lib/worktree-resolution/WorktreeRunResolution.psm1 +3 -3
- package/resources/claude-customizations/.claude/rules/architecture-boundaries.md +5 -5
- package/resources/claude-customizations/.claude/rules/csharp.md +2 -2
- package/resources/claude-customizations/.claude/rules/general-code-change.md +1 -1
- package/resources/claude-customizations/.claude/rules/general-unit-test.md +3 -2
- package/resources/claude-customizations/.claude/rules/orchestrator-state.md +153 -4
- package/resources/claude-customizations/.claude/rules/parallel-orchestration.md +50 -5
- package/resources/claude-customizations/.claude/rules/plan-acceptance-gates.md +47 -8
- package/resources/claude-customizations/.claude/rules/quality-tiers.md +11 -7
- package/resources/claude-customizations/.claude/rules/shell.md +10 -8
- package/resources/claude-customizations/.claude/rules/typescript.md +1 -1
- package/resources/claude-customizations/.claude/settings.json +3 -4
- package/resources/claude-customizations/.claude/skills/acceptance-criteria-tracking/SKILL.md +9 -1
- package/resources/claude-customizations/.claude/skills/atomic-plan-contract/SKILL.md +7 -1
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/SKILL.md +11 -3
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/scripts/cleanup-worktrees.sh +11 -2
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/scripts/cleanup_worktrees_detached_lib.sh +1 -1
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/scripts/cleanup_worktrees_enumerate_lib.sh +171 -5
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/scripts/cleanup_worktrees_preserve_lib.sh +1 -1
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/scripts/cleanup_worktrees_report_records_lib.sh +6 -43
- package/resources/claude-customizations/.claude/skills/cleanup-merged-worktrees/scripts/cleanup_worktrees_scan_helper.sh +6 -15
- package/resources/claude-customizations/.claude/skills/epic-orchestrate/SKILL.md +45 -11
- package/resources/claude-customizations/.claude/skills/epic-plan/SKILL.md +1 -1
- package/resources/claude-customizations/.claude/skills/evidence-and-timestamp-conventions/SKILL.md +13 -0
- package/resources/claude-customizations/.claude/skills/feature-promotion-lifecycle/SKILL.md +10 -0
- package/resources/claude-customizations/.claude/skills/feature-review-workflow/SKILL.md +7 -4
- package/resources/claude-customizations/.claude/skills/orchestrate/SKILL.md +42 -16
- package/resources/claude-customizations/.claude/skills/parallel-add/SKILL.md +52 -14
- package/resources/claude-customizations/.claude/skills/parallel-close/SKILL.md +22 -9
- package/resources/claude-customizations/.claude/skills/parallel-orchestrate/SKILL.md +97 -19
- package/resources/claude-customizations/.claude/skills/parallel-plan/SKILL.md +63 -7
- package/resources/claude-customizations/.claude/skills/parallel-remove/SKILL.md +35 -12
- package/resources/claude-customizations/.claude/skills/pr-author/SKILL.md +3 -1
- package/resources/claude-customizations/.claude/skills/quota-throttling/SKILL.md +1 -1
- package/resources/claude-customizations/.claude/skills/remediation-handoff-atomic-planner/SKILL.md +7 -3
- package/resources/claude-customizations/pack-manifests/core.json +25 -0
- package/resources/codex-and-agents-customizations/.agents/skills/acceptance-criteria-tracking/SKILL.md +9 -1
- package/resources/codex-and-agents-customizations/.agents/skills/architecture-boundaries/SKILL.md +5 -5
- package/resources/codex-and-agents-customizations/.agents/skills/atomic-executor/SKILL.md +11 -0
- package/resources/codex-and-agents-customizations/.agents/skills/atomic-plan-contract/SKILL.md +4 -0
- package/resources/codex-and-agents-customizations/.agents/skills/atomic-planner/SKILL.md +10 -0
- package/resources/codex-and-agents-customizations/.agents/skills/csharp/SKILL.md +2 -2
- package/resources/codex-and-agents-customizations/.agents/skills/csharp-qa-gate/SKILL.md +2 -2
- package/resources/codex-and-agents-customizations/.agents/skills/epic-orchestrate/SKILL.md +13 -3
- package/resources/codex-and-agents-customizations/.agents/skills/epic-plan/SKILL.md +17 -1
- package/resources/codex-and-agents-customizations/.agents/skills/epic-run/SKILL.md +2 -1
- package/resources/codex-and-agents-customizations/.agents/skills/evidence-and-timestamp-conventions/SKILL.md +13 -0
- package/resources/codex-and-agents-customizations/.agents/skills/feature-promotion-lifecycle/SKILL.md +1 -1
- package/resources/codex-and-agents-customizations/.agents/skills/feature-review/SKILL.md +30 -6
- package/resources/codex-and-agents-customizations/.agents/skills/feature-review-workflow/SKILL.md +16 -6
- package/resources/codex-and-agents-customizations/.agents/skills/general-code-change/SKILL.md +1 -1
- package/resources/codex-and-agents-customizations/.agents/skills/general-unit-test/SKILL.md +3 -2
- package/resources/codex-and-agents-customizations/.agents/skills/orchestrate/SKILL.md +43 -11
- package/resources/codex-and-agents-customizations/.agents/skills/orchestrator-state/SKILL.md +41 -2
- package/resources/codex-and-agents-customizations/.agents/skills/orchestrator-workflow/SKILL.md +19 -4
- package/resources/codex-and-agents-customizations/.agents/skills/quality-tiers/SKILL.md +11 -7
- package/resources/codex-and-agents-customizations/.agents/skills/remediation-handoff-atomic-planner/SKILL.md +2 -0
- package/resources/codex-and-agents-customizations/.agents/skills/translate-claude-to-codex/SKILL.md +1 -1
- package/resources/codex-and-agents-customizations/.agents-variants/csharp-legacy/skills/csharp/SKILL.md +2 -2
- package/resources/codex-and-agents-customizations/.agents-variants/csharp-legacy/skills/csharp-qa-gate/SKILL.md +2 -2
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-executor-c1.toml +11 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-executor-c2.toml +11 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-executor-c3-elevated.toml +11 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-executor-c3.toml +11 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-executor-c4.toml +11 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-executor.toml +11 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-planner-c1.toml +10 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-planner-c2.toml +10 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-planner-c3-elevated.toml +10 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-planner-c3.toml +10 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-planner-c4.toml +10 -0
- package/resources/codex-and-agents-customizations/.codex/agents/atomic-planner.toml +10 -0
- package/resources/codex-and-agents-customizations/.codex/agents/epic-orchestrator.toml +2 -1
- package/resources/codex-and-agents-customizations/.codex/agents/feature-review.toml +6 -6
- package/resources/codex-and-agents-customizations/.codex/agents/feature-reviewer-c1.toml +1 -0
- package/resources/codex-and-agents-customizations/.codex/agents/feature-reviewer-c2.toml +1 -0
- package/resources/codex-and-agents-customizations/.codex/agents/feature-reviewer-c3-elevated.toml +1 -0
- package/resources/codex-and-agents-customizations/.codex/agents/feature-reviewer-c3.toml +1 -0
- package/resources/codex-and-agents-customizations/.codex/agents/feature-reviewer-c4.toml +1 -0
- package/resources/codex-and-agents-customizations/.codex/agents/feature-reviewer.toml +1 -0
- package/resources/codex-and-agents-customizations/.codex/agents/orchestrator-c1.toml +3 -3
- package/resources/codex-and-agents-customizations/.codex/agents/orchestrator-c2.toml +3 -3
- package/resources/codex-and-agents-customizations/.codex/agents/orchestrator-c3-elevated.toml +3 -3
- package/resources/codex-and-agents-customizations/.codex/agents/orchestrator-c3.toml +3 -3
- package/resources/codex-and-agents-customizations/.codex/agents/orchestrator-c4.toml +3 -3
- package/resources/codex-and-agents-customizations/.codex/agents/orchestrator.toml +3 -3
- package/resources/codex-and-agents-customizations/.codex/codex-web-setup.sh +318 -273
- package/resources/codex-and-agents-customizations/.codex/config.toml +1 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/check-powershell-test-purity.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/check-python-test-purity.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/codex-epic-child-launch-attestation.ps1 +1 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-checkpoint-monotonic.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-codex-model-routing.ps1 +8 -2
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-completion-consistency.ps1 +97 -44
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-completion-helpers.ps1 +105 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-epic-child-worktree-binding.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-epic-merge-gate.ps1 +37 -5
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-epic-planning-only.ps1 +6 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-epic-root-invocation.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-epic-wave-barrier.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-epic-worktree-removal-gate.ps1 +54 -41
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-evidence-locations.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-orchestration-preimplementation-gate-epic-scope.ps1 +35 -14
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-orchestration-preimplementation-gate-helpers.ps1 +31 -58
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-orchestration-preimplementation-gate-modes.ps1 +63 -47
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-orchestration-preimplementation-gate-targets.ps1 +433 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-orchestration-preimplementation-gate.ps1 +24 -11
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-powershell-batch-budget.ps1 +8 -2
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-promotion-mcp-only.ps1 +13 -4
- package/resources/codex-and-agents-customizations/.codex/hooks/enforce-python-batch-budget.ps1 +8 -2
- package/resources/codex-and-agents-customizations/.codex/hooks/feature-folder-resolution.ps1 +373 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/feature-review-coverage-thresholds.ps1 +85 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-command-heredoc.ps1 +119 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-command-invocation-operands.ps1 +198 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-command-invocation.ps1 +254 -255
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-command-payload-powershell.ps1 +201 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-command-payload.ps1 +484 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-command-scanner.ps1 +27 -110
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-dependency-guard.ps1 +114 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/hook-docs-only-diff.ps1 +493 -0
- package/resources/codex-and-agents-customizations/.codex/hooks/validate-bash.ps1 +8 -2
- package/resources/codex-and-agents-customizations/.codex/hooks/validate-codex-subagent-routing.ps1 +7 -1
- package/resources/codex-and-agents-customizations/.codex/hooks/validate-feature-review-coverage.ps1 +24 -8
- package/resources/codex-and-agents-customizations/pack-manifests/core.json +9 -0
- package/resources/customizations/.github/agents/csharp-typed-engineer.agent.md +2 -2
- package/resources/customizations/.github/instructions/csharp-code-change.instructions.md +4 -4
- package/resources/customizations/.github/instructions/csharp-unit-test.instructions.md +2 -2
- package/resources/customizations/.github/skills/acceptance-criteria-tracking/SKILL.md +9 -1
- package/resources/customizations/.github/skills/atomic-plan-contract/SKILL.md +4 -0
- package/resources/customizations/.github/skills/evidence-and-timestamp-conventions/SKILL.md +13 -0
- package/resources/customizations/.github/skills/feature-review-workflow/SKILL.md +1 -1
- package/resources/powershell/PoshQC/PoshQC.Coverage.psm1 +314 -0
- package/resources/powershell/PoshQC/PoshQC.Testing.psm1 +25 -28
- package/resources/powershell/PoshQC/PoshQC.psm1 +1 -0
- package/resources/powershell/PoshQC/README.md +8 -2
- package/resources/powershell/PoshQC/settings/pester.runsettings.psd1 +2 -315
|
@@ -0,0 +1,337 @@
|
|
|
1
|
+
<#
|
|
2
|
+
.SYNOPSIS
|
|
3
|
+
Portable remediation-loop review-outcome and accounting checks (R5-R11).
|
|
4
|
+
|
|
5
|
+
.DESCRIPTION
|
|
6
|
+
Destination-runtime PowerShell port of the issue #484 invariants the
|
|
7
|
+
authoritative Python validator applies to a checkpoint's remediation_loop:
|
|
8
|
+
the review-outcome rules R8a, R8b, R9a-R9d, and R10, and the accounting
|
|
9
|
+
rules R5, R6, R7a, R7b, and R11, matching the error-string templates in
|
|
10
|
+
`scripts/dev_tools/_orchestrator_state_remediation_loop.py` and the rules
|
|
11
|
+
document `.claude/rules/orchestrator-state.md`.
|
|
12
|
+
|
|
13
|
+
The receipts module calls the exported entry point after its unchanged
|
|
14
|
+
per-cycle checks, passing the cycle list or $null when cycles is absent or
|
|
15
|
+
not a list, so the new checks also run for a loop with review outcomes and
|
|
16
|
+
no cycles.
|
|
17
|
+
|
|
18
|
+
Every comparison against the verdict and class vocabulary is case-sensitive
|
|
19
|
+
(-ccontains, -cnotcontains, -ceq). An integer is a JSON number deserialized
|
|
20
|
+
as [int] or [long]; a boolean is never an integer. Values interpolated into
|
|
21
|
+
a message ({v}) render through ConvertTo-PythonDisplayText so the text
|
|
22
|
+
matches Python's str().
|
|
23
|
+
|
|
24
|
+
Every function is pure: it reads no file, starts no process, and never
|
|
25
|
+
mutates its input. Each check returns a string array, empty when valid.
|
|
26
|
+
CONVENTION: this module fails fast at module scope and imports its siblings with -ErrorAction Stop.
|
|
27
|
+
#>
|
|
28
|
+
|
|
29
|
+
Set-StrictMode -Version Latest
|
|
30
|
+
$ErrorActionPreference = 'Stop'
|
|
31
|
+
|
|
32
|
+
# Import the shared checkpoint-value primitives, resolved relative to this
|
|
33
|
+
# module's directory so the import travels with the pushed-down pack.
|
|
34
|
+
Import-Module (Join-Path -Path $PSScriptRoot -ChildPath 'OrchestratorStateCheckpointValue.psm1') -Force -ErrorAction Stop
|
|
35
|
+
|
|
36
|
+
# Loop and cycle keys read by the accounting rules.
|
|
37
|
+
$script:REVIEW_OUTCOMES_KEY = 'review_outcomes'
|
|
38
|
+
$script:COMPLETED_ATTEMPTS_KEY = 'completed_attempts'
|
|
39
|
+
$script:CANDIDATE_APPLIED_KEY = 'candidate_applied'
|
|
40
|
+
$script:OPENED_BY_REVIEW_KEY = 'opened_by_review'
|
|
41
|
+
$script:COMPLETED_EXECUTION_STATUS = 'complete'
|
|
42
|
+
|
|
43
|
+
# Review verdicts and remediability classes in spec table order, and the two
|
|
44
|
+
# derived class partitions. Pinned to the Python constants of the same names.
|
|
45
|
+
$script:REVIEW_VERDICTS = @('PASS', 'REMEDIATION_REQUIRED', 'HALT_NON_REMEDIABLE', 'AWAITING_CI')
|
|
46
|
+
$script:REMEDIABILITY_CLASSES = @('autonomous', 'external_dependency', 'policy_hold', 'awaiting_ci', 'human_decision_required')
|
|
47
|
+
$script:NON_REMEDIABLE_CLASSES = @('external_dependency', 'policy_hold', 'awaiting_ci', 'human_decision_required')
|
|
48
|
+
$script:HALT_CLASSES = @('external_dependency', 'policy_hold', 'human_decision_required')
|
|
49
|
+
$script:REMEDIABLE_CLASS = 'autonomous'
|
|
50
|
+
$script:REMEDIATION_REQUIRED_VERDICT = 'REMEDIATION_REQUIRED'
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
function Test-RemediationStrictInteger {
|
|
54
|
+
<#
|
|
55
|
+
.SYNOPSIS
|
|
56
|
+
Report whether a deserialized JSON value is an integer and not a boolean.
|
|
57
|
+
.DESCRIPTION
|
|
58
|
+
Private predicate mirroring Python's isinstance(value, int) and not
|
|
59
|
+
isinstance(value, bool). ConvertFrom-Json materializes a JSON integer as
|
|
60
|
+
[int] or [long] and a JSON boolean as [bool].
|
|
61
|
+
.PARAMETER Value
|
|
62
|
+
The deserialized JSON value to classify. May be $null.
|
|
63
|
+
.OUTPUTS
|
|
64
|
+
System.Boolean - $true only for an [int] or [long] value.
|
|
65
|
+
#>
|
|
66
|
+
[CmdletBinding()]
|
|
67
|
+
[OutputType([bool])]
|
|
68
|
+
param(
|
|
69
|
+
[Parameter(Mandatory = $true)]
|
|
70
|
+
[AllowNull()]
|
|
71
|
+
[object] $Value
|
|
72
|
+
)
|
|
73
|
+
|
|
74
|
+
return (($Value -is [int]) -or ($Value -is [long])) -and -not ($Value -is [bool])
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
function Get-RemediationReviewVerdict {
|
|
78
|
+
<#
|
|
79
|
+
.SYNOPSIS
|
|
80
|
+
Derive a review verdict from its findings' remediability classes.
|
|
81
|
+
.DESCRIPTION
|
|
82
|
+
Private helper mirroring derive_review_verdict. Evaluates, in order: no
|
|
83
|
+
classes yields PASS; any autonomous class yields REMEDIATION_REQUIRED;
|
|
84
|
+
any member of HALT_CLASSES yields HALT_NON_REMEDIABLE; otherwise
|
|
85
|
+
AWAITING_CI. A member outside REMEDIABILITY_CLASSES (compared
|
|
86
|
+
case-sensitively) raises a terminating error whose message begins
|
|
87
|
+
'invalid remediability: '.
|
|
88
|
+
.PARAMETER Remediability
|
|
89
|
+
The remediability class of every blocking finding; may be empty and may
|
|
90
|
+
repeat a class.
|
|
91
|
+
.OUTPUTS
|
|
92
|
+
System.String - one of the four review verdicts.
|
|
93
|
+
#>
|
|
94
|
+
[CmdletBinding()]
|
|
95
|
+
[OutputType([string])]
|
|
96
|
+
param(
|
|
97
|
+
[Parameter(Mandatory = $true)]
|
|
98
|
+
[AllowEmptyCollection()]
|
|
99
|
+
[string[]] $Remediability
|
|
100
|
+
)
|
|
101
|
+
|
|
102
|
+
foreach ($value in $Remediability) {
|
|
103
|
+
if ($script:REMEDIABILITY_CLASSES -cnotcontains $value) {
|
|
104
|
+
throw "invalid remediability: $value"
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
if ($Remediability.Count -eq 0) { return 'PASS' }
|
|
109
|
+
if ($Remediability -ccontains $script:REMEDIABLE_CLASS) { return 'REMEDIATION_REQUIRED' }
|
|
110
|
+
foreach ($value in $Remediability) {
|
|
111
|
+
if ($script:HALT_CLASSES -ccontains $value) { return 'HALT_NON_REMEDIABLE' }
|
|
112
|
+
}
|
|
113
|
+
return 'AWAITING_CI'
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
function Get-RemediationReviewOutcomeError {
|
|
117
|
+
<#
|
|
118
|
+
.SYNOPSIS
|
|
119
|
+
Return one review outcome's errors (R9a-R9d, then R10).
|
|
120
|
+
.DESCRIPTION
|
|
121
|
+
Private helper mirroring _validate_review_outcome. Checks the verdict
|
|
122
|
+
(string check before membership), the findings list, and each finding's
|
|
123
|
+
remediability (string check before membership); R10 runs only when none
|
|
124
|
+
of those checks produced an error for the outcome.
|
|
125
|
+
.PARAMETER Index
|
|
126
|
+
The outcome's zero-based position, used for error context.
|
|
127
|
+
.PARAMETER Outcome
|
|
128
|
+
The deserialized outcome object.
|
|
129
|
+
.OUTPUTS
|
|
130
|
+
System.String[] - zero or more error strings.
|
|
131
|
+
#>
|
|
132
|
+
[CmdletBinding()]
|
|
133
|
+
[OutputType([string[]])]
|
|
134
|
+
param(
|
|
135
|
+
[Parameter(Mandatory = $true)]
|
|
136
|
+
[int] $Index,
|
|
137
|
+
|
|
138
|
+
[Parameter(Mandatory = $true)]
|
|
139
|
+
[psobject] $Outcome
|
|
140
|
+
)
|
|
141
|
+
|
|
142
|
+
$errors = [System.Collections.Generic.List[string]]::new()
|
|
143
|
+
$prefix = "Checkpoint remediation review outcome #$Index"
|
|
144
|
+
|
|
145
|
+
$verdict = (Get-CheckpointObjectMember -Owner $Outcome -Name 'verdict').Value
|
|
146
|
+
if (-not ($verdict -is [string]) -or ($script:REVIEW_VERDICTS -cnotcontains [string]$verdict)) {
|
|
147
|
+
$rendered = ConvertTo-PythonDisplayText -Value $verdict
|
|
148
|
+
$errors.Add("$prefix verdict must be one of PASS, REMEDIATION_REQUIRED, HALT_NON_REMEDIABLE, AWAITING_CI; got: $rendered")
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
$classes = [System.Collections.Generic.List[string]]::new()
|
|
152
|
+
$findings = (Get-CheckpointObjectMember -Owner $Outcome -Name 'findings').Value
|
|
153
|
+
if (-not (Test-CheckpointListValue -Value $findings)) {
|
|
154
|
+
$errors.Add("$prefix findings must be a list.")
|
|
155
|
+
} else {
|
|
156
|
+
$findingIndex = 0
|
|
157
|
+
foreach ($finding in @($findings)) {
|
|
158
|
+
if (-not (Test-CheckpointObjectValue -Value $finding)) {
|
|
159
|
+
$errors.Add("$prefix finding #$findingIndex must be an object.")
|
|
160
|
+
} else {
|
|
161
|
+
$remediability = (Get-CheckpointObjectMember -Owner $finding -Name 'remediability').Value
|
|
162
|
+
if (-not ($remediability -is [string]) -or ($script:REMEDIABILITY_CLASSES -cnotcontains [string]$remediability)) {
|
|
163
|
+
$rendered = ConvertTo-PythonDisplayText -Value $remediability
|
|
164
|
+
$errors.Add("$prefix finding #$findingIndex remediability must be one of autonomous, external_dependency, policy_hold, awaiting_ci, human_decision_required; got: $rendered")
|
|
165
|
+
} else {
|
|
166
|
+
$classes.Add([string]$remediability)
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
$findingIndex++
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
# R10 compares only a well-formed outcome; any shape error above suppresses it.
|
|
174
|
+
if ($errors.Count -eq 0) {
|
|
175
|
+
$expected = Get-RemediationReviewVerdict -Remediability $classes.ToArray()
|
|
176
|
+
if (-not ([string]$verdict -ceq $expected)) {
|
|
177
|
+
$errors.Add("$prefix verdict $verdict does not match its findings (expected $expected).")
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
return $errors.ToArray()
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
function Get-RemediationReviewOutcomeListError {
|
|
185
|
+
<#
|
|
186
|
+
.SYNOPSIS
|
|
187
|
+
Return the review-outcome errors (R8a, R8b, then each outcome).
|
|
188
|
+
.DESCRIPTION
|
|
189
|
+
Private helper mirroring _validate_review_outcomes. An absent
|
|
190
|
+
review_outcomes key yields no errors; a present non-list value yields R8a
|
|
191
|
+
alone; otherwise each non-object outcome yields R8b and is skipped.
|
|
192
|
+
.PARAMETER RemediationLoop
|
|
193
|
+
The deserialized remediation_loop object.
|
|
194
|
+
.OUTPUTS
|
|
195
|
+
System.String[] - zero or more error strings.
|
|
196
|
+
#>
|
|
197
|
+
[CmdletBinding()]
|
|
198
|
+
[OutputType([string[]])]
|
|
199
|
+
param(
|
|
200
|
+
[Parameter(Mandatory = $true)]
|
|
201
|
+
[psobject] $RemediationLoop
|
|
202
|
+
)
|
|
203
|
+
|
|
204
|
+
$errors = [System.Collections.Generic.List[string]]::new()
|
|
205
|
+
$member = Get-CheckpointObjectMember -Owner $RemediationLoop -Name $script:REVIEW_OUTCOMES_KEY
|
|
206
|
+
if (-not $member.Present) { return $errors.ToArray() }
|
|
207
|
+
if (-not (Test-CheckpointListValue -Value $member.Value)) {
|
|
208
|
+
$errors.Add('Checkpoint remediation_loop review_outcomes must be a list.')
|
|
209
|
+
return $errors.ToArray()
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
$index = 0
|
|
213
|
+
foreach ($outcome in @($member.Value)) {
|
|
214
|
+
if (-not (Test-CheckpointObjectValue -Value $outcome)) {
|
|
215
|
+
$errors.Add("Checkpoint remediation review outcome #$index must be an object.")
|
|
216
|
+
} else {
|
|
217
|
+
$errors.AddRange([string[]]@(Get-RemediationReviewOutcomeError -Index $index -Outcome $outcome))
|
|
218
|
+
}
|
|
219
|
+
$index++
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
return $errors.ToArray()
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
function Test-RemediationOpenedByReview {
|
|
226
|
+
<#
|
|
227
|
+
.SYNOPSIS
|
|
228
|
+
Report whether an index names a REMEDIATION_REQUIRED outcome object.
|
|
229
|
+
.DESCRIPTION
|
|
230
|
+
Private predicate for R11: the value must be an integer (not a boolean)
|
|
231
|
+
from 0 to one less than the outcome count of a list review_outcomes, and
|
|
232
|
+
the indexed entry must be an object whose verdict is exactly
|
|
233
|
+
REMEDIATION_REQUIRED. A negative index is out of range.
|
|
234
|
+
.PARAMETER OpenedByReview
|
|
235
|
+
The raw opened_by_review value. May be $null.
|
|
236
|
+
.PARAMETER Outcomes
|
|
237
|
+
The raw review_outcomes value. May be $null.
|
|
238
|
+
.OUTPUTS
|
|
239
|
+
System.Boolean - $true only when the reference is valid.
|
|
240
|
+
#>
|
|
241
|
+
[CmdletBinding()]
|
|
242
|
+
[OutputType([bool])]
|
|
243
|
+
param(
|
|
244
|
+
[Parameter(Mandatory = $true)]
|
|
245
|
+
[AllowNull()]
|
|
246
|
+
[object] $OpenedByReview,
|
|
247
|
+
|
|
248
|
+
[Parameter(Mandatory = $true)]
|
|
249
|
+
[AllowNull()]
|
|
250
|
+
[object] $Outcomes
|
|
251
|
+
)
|
|
252
|
+
|
|
253
|
+
if (-not (Test-RemediationStrictInteger -Value $OpenedByReview)) { return $false }
|
|
254
|
+
if (-not (Test-CheckpointListValue -Value $Outcomes)) { return $false }
|
|
255
|
+
$outcomeList = @($Outcomes)
|
|
256
|
+
if ($OpenedByReview -lt 0 -or $OpenedByReview -ge $outcomeList.Count) { return $false }
|
|
257
|
+
$target = $outcomeList[[int]$OpenedByReview]
|
|
258
|
+
if (-not (Test-CheckpointObjectValue -Value $target)) { return $false }
|
|
259
|
+
$verdict = (Get-CheckpointObjectMember -Owner $target -Name 'verdict').Value
|
|
260
|
+
return ($verdict -is [string]) -and ([string]$verdict -ceq $script:REMEDIATION_REQUIRED_VERDICT)
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
function Get-OrchestratorStateRemediationAccountingError {
|
|
264
|
+
<#
|
|
265
|
+
.SYNOPSIS
|
|
266
|
+
Return the remediation_loop review-outcome and accounting errors (R5-R11).
|
|
267
|
+
.DESCRIPTION
|
|
268
|
+
Public entry mirroring the issue #484 tail of _validate_remediation_loop.
|
|
269
|
+
Returns, in order: the review-outcome errors (R8a; otherwise per outcome
|
|
270
|
+
R8b, R9a, R9b, R9c or R9d per finding, then R10); then, for each object
|
|
271
|
+
cycle in order, R5, R6, and R11; then R7a, otherwise R7b. With none of the
|
|
272
|
+
new keys present it returns nothing.
|
|
273
|
+
.PARAMETER RemediationLoop
|
|
274
|
+
The deserialized remediation_loop object.
|
|
275
|
+
.PARAMETER Cycle
|
|
276
|
+
The loop's cycles list, or $null when cycles is absent or not a list.
|
|
277
|
+
.OUTPUTS
|
|
278
|
+
System.String[] - zero or more error strings.
|
|
279
|
+
#>
|
|
280
|
+
[CmdletBinding()]
|
|
281
|
+
[OutputType([string[]])]
|
|
282
|
+
param(
|
|
283
|
+
[Parameter(Mandatory = $true)]
|
|
284
|
+
[psobject] $RemediationLoop,
|
|
285
|
+
|
|
286
|
+
[Parameter(Mandatory = $true)]
|
|
287
|
+
[AllowNull()]
|
|
288
|
+
[AllowEmptyCollection()]
|
|
289
|
+
[object] $Cycle
|
|
290
|
+
)
|
|
291
|
+
|
|
292
|
+
$errors = [System.Collections.Generic.List[string]]::new()
|
|
293
|
+
$errors.AddRange([string[]]@(Get-RemediationReviewOutcomeListError -RemediationLoop $RemediationLoop))
|
|
294
|
+
|
|
295
|
+
$outcomes = (Get-CheckpointObjectMember -Owner $RemediationLoop -Name $script:REVIEW_OUTCOMES_KEY).Value
|
|
296
|
+
$appliedCount = 0
|
|
297
|
+
$cycleItems = @()
|
|
298
|
+
if ($null -ne $Cycle) { $cycleItems = @($Cycle) }
|
|
299
|
+
$index = 0
|
|
300
|
+
foreach ($item in $cycleItems) {
|
|
301
|
+
if (Test-CheckpointObjectValue -Value $item) {
|
|
302
|
+
$prefix = "Checkpoint remediation cycle #$index"
|
|
303
|
+
$applied = Get-CheckpointObjectMember -Owner $item -Name $script:CANDIDATE_APPLIED_KEY
|
|
304
|
+
if ($applied.Present) {
|
|
305
|
+
if (-not ($applied.Value -is [bool])) {
|
|
306
|
+
$errors.Add("$prefix candidate_applied must be a boolean.")
|
|
307
|
+
} elseif ($applied.Value) {
|
|
308
|
+
$appliedCount++
|
|
309
|
+
$executionStatus = (Get-CheckpointObjectMember -Owner $item -Name 'execution_status').Value
|
|
310
|
+
if (-not ($executionStatus -is [string]) -or -not ([string]$executionStatus -ceq $script:COMPLETED_EXECUTION_STATUS)) {
|
|
311
|
+
$errors.Add("$prefix candidate_applied is true but execution_status is not 'complete'.")
|
|
312
|
+
}
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
$opened = Get-CheckpointObjectMember -Owner $item -Name $script:OPENED_BY_REVIEW_KEY
|
|
316
|
+
if ($opened.Present -and -not (Test-RemediationOpenedByReview -OpenedByReview $opened.Value -Outcomes $outcomes)) {
|
|
317
|
+
$errors.Add("$prefix opened_by_review must reference a review outcome whose verdict is REMEDIATION_REQUIRED.")
|
|
318
|
+
}
|
|
319
|
+
}
|
|
320
|
+
$index++
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
$attempts = Get-CheckpointObjectMember -Owner $RemediationLoop -Name $script:COMPLETED_ATTEMPTS_KEY
|
|
324
|
+
if ($attempts.Present) {
|
|
325
|
+
if (-not (Test-RemediationStrictInteger -Value $attempts.Value) -or $attempts.Value -lt 0) {
|
|
326
|
+
$errors.Add('Checkpoint remediation_loop completed_attempts must be a non-negative integer.')
|
|
327
|
+
} elseif ($attempts.Value -ne $appliedCount) {
|
|
328
|
+
$errors.Add("Checkpoint remediation_loop completed_attempts is $($attempts.Value) but $appliedCount cycles have candidate_applied true.")
|
|
329
|
+
}
|
|
330
|
+
}
|
|
331
|
+
|
|
332
|
+
return $errors.ToArray()
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
# Only the entry point is exported; the verdict helper and the per-outcome and
|
|
336
|
+
# per-reference checks stay private to this module.
|
|
337
|
+
Export-ModuleMember -Function Get-OrchestratorStateRemediationAccountingError
|
|
@@ -5,7 +5,8 @@
|
|
|
5
5
|
.DESCRIPTION
|
|
6
6
|
Destination-runtime PowerShell port of `validate_routing_contract` in
|
|
7
7
|
`scripts/dev_tools/_orchestrator_state_routing.py`, covering parity-inventory
|
|
8
|
-
rows C6.1 through C6.
|
|
8
|
+
rows C6.1 through C6.15. The C6.15 adoption waiver affects only receipt
|
|
9
|
+
presence (C6.9); the declared-list equality checks are unchanged:
|
|
9
10
|
|
|
10
11
|
C6.1 routing matrix carries no routes object (returns)
|
|
11
12
|
C6.2 no route selected (returns)
|
|
@@ -21,6 +22,7 @@
|
|
|
21
22
|
C6.12 lifecycle_operations must be a list when present
|
|
22
23
|
C6.13 per non-object lifecycle operation
|
|
23
24
|
C6.14 per lifecycle operation that did not use the MCP surface
|
|
25
|
+
C6.15 issue_adoption field and waiver rules (OrchestratorStateIssueAdoption.psm1)
|
|
24
26
|
|
|
25
27
|
The routing matrix is read from `OrchestratorStateRoutingMatrix.psm1`, which
|
|
26
28
|
implements deviation PD-1: the constants are pinned and no disk read occurs at
|
|
@@ -56,6 +58,7 @@ $ErrorActionPreference = 'Stop'
|
|
|
56
58
|
# pushed-down pack regardless of the working directory.
|
|
57
59
|
Import-Module (Join-Path -Path $PSScriptRoot -ChildPath 'OrchestratorStateCheckpointValue.psm1') -Force -ErrorAction Stop
|
|
58
60
|
Import-Module (Join-Path -Path $PSScriptRoot -ChildPath 'OrchestratorStateRoutingMatrix.psm1') -Force -ErrorAction Stop
|
|
61
|
+
Import-Module (Join-Path -Path $PSScriptRoot -ChildPath 'OrchestratorStateIssueAdoption.psm1') -Force -ErrorAction Stop
|
|
59
62
|
|
|
60
63
|
# The promotion-entry MCP tools and the promotion type that triggers substitution.
|
|
61
64
|
$script:FEATURE_PROMOTION_ENTRY_TOOL = 'new_potential_entry'
|
|
@@ -410,11 +413,16 @@ function Get-OrchestratorStateRoutingContractError {
|
|
|
410
413
|
}
|
|
411
414
|
|
|
412
415
|
$actualTools = @(Get-CheckpointAcknowledgedName -State $State -ArrayKey 'mcp_call_receipts' -NameKey 'tool' -FlagKey 'ok')
|
|
416
|
+
# C6.15: a valid issue_adoption record waives the receipt requirement for the
|
|
417
|
+
# tools it lists; any adoption error waives nothing.
|
|
418
|
+
$adoption = Get-OrchestratorStateIssueAdoptionResult -State $State -RouteId $routeId -RequiredMcpTool ([string[]]$requiredMcpTools) -SuccessfulTool ([string[]]$actualTools)
|
|
413
419
|
foreach ($tool in $requiredMcpTools) {
|
|
420
|
+
if (@($adoption.WaivedTools) -ccontains $tool) { continue }
|
|
414
421
|
if ($actualTools -cnotcontains $tool) {
|
|
415
422
|
$errors.Add("Checkpoint missing successful MCP receipt: $tool.")
|
|
416
423
|
}
|
|
417
424
|
}
|
|
425
|
+
$errors.AddRange([string[]]@($adoption.Errors))
|
|
418
426
|
|
|
419
427
|
# C6.10 to C6.14: the two empty-list fields and the lifecycle operations.
|
|
420
428
|
foreach ($key in $script:COMPLETION_EMPTY_LIST_KEYS) {
|
package/resources/claude-customizations/.claude/lib/worktree-resolution/WorktreeItemResolution.psm1
CHANGED
|
@@ -21,7 +21,8 @@
|
|
|
21
21
|
PowerShell 7+. Re-uses its siblings for enumeration, the marker test, the ascent,
|
|
22
22
|
the branch reader, normalisation, the join, the result constructor, and both
|
|
23
23
|
reason-code accessors, re-implementing none. Neither reason-code literal appears
|
|
24
|
-
here. Its only filesystem read is the checkpoint-text seam
|
|
24
|
+
here. Its only filesystem read is still the checkpoint-text seam, including for the
|
|
25
|
+
item-by-pull-request resolver added for issue #850. Mirrored byte-identically.
|
|
25
26
|
CONVENTION: this module fails fast at module scope and imports its siblings with -ErrorAction Stop.
|
|
26
27
|
#>
|
|
27
28
|
|
|
@@ -395,6 +396,81 @@ function Resolve-WorktreeItemTarget {
|
|
|
395
396
|
return (Resolve-WorktreeItemTargetByIssue -Session $session -Issue $issues[0])
|
|
396
397
|
}
|
|
397
398
|
|
|
399
|
+
# Private: whether checkpoint text records a pull request number in pr_gate.pr_number or
|
|
400
|
+
# in a standalone_merge_authorizations entry whose pr_number is a positive JSON integer.
|
|
401
|
+
function Test-WorktreeItemCheckpointRecordsPr {
|
|
402
|
+
[CmdletBinding()]
|
|
403
|
+
[OutputType([bool])]
|
|
404
|
+
param(
|
|
405
|
+
[Parameter(Mandatory = $true)] [AllowNull()] [AllowEmptyString()] [string] $Text,
|
|
406
|
+
[Parameter(Mandatory = $true)] [long] $PrNumber
|
|
407
|
+
)
|
|
408
|
+
|
|
409
|
+
if ([string]::IsNullOrWhiteSpace($Text)) { return $false }
|
|
410
|
+
$payload = $null
|
|
411
|
+
try { $payload = $Text | ConvertFrom-Json } catch { return $false }
|
|
412
|
+
if ($null -eq $payload -or $payload -isnot [pscustomobject]) { return $false }
|
|
413
|
+
# Names are collected per property, because strict mode throws on .Name of an empty object.
|
|
414
|
+
$names = @($payload.PSObject.Properties | ForEach-Object { $_.Name })
|
|
415
|
+
if ($names -contains 'pr_gate' -and $payload.pr_gate -is [pscustomobject] -and @($payload.pr_gate.PSObject.Properties | ForEach-Object { $_.Name }) -contains 'pr_number') {
|
|
416
|
+
$recorded = [long] 0
|
|
417
|
+
if ([long]::TryParse([string] $payload.pr_gate.pr_number, [ref] $recorded) -and $recorded -eq $PrNumber) { return $true }
|
|
418
|
+
}
|
|
419
|
+
if ($names -notcontains 'standalone_merge_authorizations') { return $false }
|
|
420
|
+
foreach ($entry in @($payload.standalone_merge_authorizations)) {
|
|
421
|
+
if ($entry -isnot [pscustomobject] -or @($entry.PSObject.Properties | ForEach-Object { $_.Name }) -notcontains 'pr_number') { continue }
|
|
422
|
+
$value = $entry.pr_number
|
|
423
|
+
# Only a JSON integer counts; a string, fraction, zero, or negative never matches.
|
|
424
|
+
if (($value -is [int] -or $value -is [long]) -and $value -gt 0 -and [long] $value -eq $PrNumber) { return $true }
|
|
425
|
+
}
|
|
426
|
+
return $false
|
|
427
|
+
}
|
|
428
|
+
|
|
429
|
+
function Resolve-WorktreeItemTargetByPrNumber {
|
|
430
|
+
<#
|
|
431
|
+
.SYNOPSIS
|
|
432
|
+
Resolve the live worktree whose orchestrator checkpoint records a pull request number (issue #850).
|
|
433
|
+
.DESCRIPTION
|
|
434
|
+
Keeps each live root whose checkpoint records the number in pr_gate.pr_number or
|
|
435
|
+
in a standalone_merge_authorizations entry. Zero matches resolve NoTarget, one
|
|
436
|
+
resolves, and several are Ambiguous with no tie-break. A number of zero or less
|
|
437
|
+
is NoTarget. Reads only through the checkpoint-text seam.
|
|
438
|
+
.PARAMETER PrNumber
|
|
439
|
+
The pull request number the command names.
|
|
440
|
+
.PARAMETER SessionRoot
|
|
441
|
+
The calling process's path, used only to find the repository and label a result.
|
|
442
|
+
Defaults to the current location when blank.
|
|
443
|
+
#>
|
|
444
|
+
[CmdletBinding()]
|
|
445
|
+
[OutputType([pscustomobject])]
|
|
446
|
+
param(
|
|
447
|
+
[Parameter(Mandatory = $true)] [long] $PrNumber,
|
|
448
|
+
[Parameter(Mandatory = $true)] [AllowEmptyString()] [string] $SessionRoot
|
|
449
|
+
)
|
|
450
|
+
|
|
451
|
+
$session = if ([string]::IsNullOrWhiteSpace($SessionRoot)) { (Get-Location).ProviderPath } else { $SessionRoot }
|
|
452
|
+
$noTarget = "pull request {0} is recorded in pr_gate.pr_number or a standalone_merge_authorizations entry of no live worktree's orchestrator checkpoint" -f $PrNumber
|
|
453
|
+
if ($PrNumber -le 0) {
|
|
454
|
+
return (New-WorktreeResolutionTargetResult -Status 'NoTarget' -SessionRoot $session -Detail $noTarget)
|
|
455
|
+
}
|
|
456
|
+
# Assigned before it is wrapped, for the reason recorded in the branch resolver.
|
|
457
|
+
$liveRoots = Get-WorktreeItemLiveRoot -SessionRoot $session
|
|
458
|
+
$matched = [System.Collections.Generic.List[string]]::new()
|
|
459
|
+
foreach ($root in @($liveRoots)) {
|
|
460
|
+
$text = Get-WorktreeItemCheckpointText -Path (Get-WorktreeItemCheckpointPath -WorktreeRoot $root)
|
|
461
|
+
if (Test-WorktreeItemCheckpointRecordsPr -Text $text -PrNumber $PrNumber) { $matched.Add($root) }
|
|
462
|
+
}
|
|
463
|
+
if ($matched.Count -eq 0) {
|
|
464
|
+
return (New-WorktreeResolutionTargetResult -Status 'NoTarget' -SessionRoot $session -Detail $noTarget)
|
|
465
|
+
}
|
|
466
|
+
if ($matched.Count -eq 1) {
|
|
467
|
+
return (ConvertTo-WorktreeItemResolvedResult -WorktreeRoot $matched[0] -SessionRoot $session -Detail (
|
|
468
|
+
"pull request {0} resolves to the live worktree whose orchestrator checkpoint records it" -f $PrNumber))
|
|
469
|
+
}
|
|
470
|
+
return (New-WorktreeResolutionTargetResult -Status 'Ambiguous' -SessionRoot $session -Candidate $matched.ToArray() -Detail (
|
|
471
|
+
"pull request {0} is recorded in the orchestrator checkpoints of {1} live worktrees; move the stale checkpoint to artifacts/orchestration/handoff/ so that one worktree records it" -f $PrNumber, $matched.Count))
|
|
472
|
+
}
|
|
473
|
+
|
|
398
474
|
Export-ModuleMember -Function `
|
|
399
475
|
Get-WorktreeItemCheckpointRelativePath, `
|
|
400
476
|
Get-WorktreeItemCheckpointPath, `
|
|
@@ -404,4 +480,5 @@ Export-ModuleMember -Function `
|
|
|
404
480
|
Get-WorktreeItemCheckpointIssue, `
|
|
405
481
|
Get-WorktreeItemLiveRoot, `
|
|
406
482
|
ConvertTo-WorktreeItemResolvedResult, `
|
|
407
|
-
Resolve-WorktreeItemTarget
|
|
483
|
+
Resolve-WorktreeItemTarget, `
|
|
484
|
+
Resolve-WorktreeItemTargetByPrNumber
|
package/resources/claude-customizations/.claude/lib/worktree-resolution/WorktreeRunResolution.psm1
CHANGED
|
@@ -340,7 +340,7 @@ function Resolve-WorktreeParallelTarget {
|
|
|
340
340
|
}
|
|
341
341
|
|
|
342
342
|
# Private: compare two worktree paths, insensitive to separator style and trailing
|
|
343
|
-
# slashes, and case-insensitive
|
|
343
|
+
# slashes, and case-insensitive for drive-letter and UNC (//) paths.
|
|
344
344
|
function Test-WorktreeRunPathEqual {
|
|
345
345
|
[CmdletBinding()]
|
|
346
346
|
[OutputType([bool])]
|
|
@@ -352,8 +352,8 @@ function Test-WorktreeRunPathEqual {
|
|
|
352
352
|
if ([string]::IsNullOrWhiteSpace($Left) -or [string]::IsNullOrWhiteSpace($Right)) { return $false }
|
|
353
353
|
$a = ($Left.Trim() -replace '\\', '/').TrimEnd('/')
|
|
354
354
|
$b = ($Right.Trim() -replace '\\', '/').TrimEnd('/')
|
|
355
|
-
$
|
|
356
|
-
$comparison = if ($
|
|
355
|
+
$isCaseInsensitivePath = ($a -match '^([A-Za-z]:|//)') -or ($b -match '^([A-Za-z]:|//)')
|
|
356
|
+
$comparison = if ($isCaseInsensitivePath) { [System.StringComparison]::OrdinalIgnoreCase } else { [System.StringComparison]::Ordinal }
|
|
357
357
|
return [string]::Equals($a, $b, $comparison)
|
|
358
358
|
}
|
|
359
359
|
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
paths:
|
|
3
3
|
- "**/*.ts"
|
|
4
4
|
- "**/*.cs"
|
|
5
|
-
description: Architecture boundary enforcement rules for
|
|
5
|
+
description: Architecture boundary enforcement rules for a host-neutral layered architecture.
|
|
6
6
|
---
|
|
7
7
|
|
|
8
8
|
# Architecture Boundaries
|
|
@@ -14,7 +14,7 @@ Architecture boundary enforcement is a uniform gate across all tiers (T1–T4).
|
|
|
14
14
|
- **TypeScript:** `dependency-cruiser`. Configuration file pattern: `.dependency-cruiser.cjs`.
|
|
15
15
|
- **.NET (when the backend exists):** `NetArchTest.Rules`. Test project naming pattern: `*.ArchitectureTests`.
|
|
16
16
|
|
|
17
|
-
##
|
|
17
|
+
## Host-Neutral Architecture Rules (enforceable assertions)
|
|
18
18
|
|
|
19
19
|
Production code in this repository must satisfy each of the following assertions. Each assertion is enforced by `dependency-cruiser` (TypeScript) or `NetArchTest.Rules` (.NET) where applicable; legacy import utilities, when added, must satisfy the same assertions.
|
|
20
20
|
|
|
@@ -37,9 +37,9 @@ Production code in this repository must satisfy each of the following assertions
|
|
|
37
37
|
|
|
38
38
|
## Layer Boundary Assertions (.NET, applies once the backend exists)
|
|
39
39
|
|
|
40
|
-
-
|
|
41
|
-
-
|
|
42
|
-
- Adapter projects may depend on
|
|
40
|
+
- `<Product>.Domain` must have zero references to Outlook PIA, VSTO, or Office.js types.
|
|
41
|
+
- `<Product>.Application` may depend on `<Product>.Domain` only.
|
|
42
|
+
- Adapter projects may depend on `<Product>.Domain` and `<Product>.Application`; domain may not depend on adapters.
|
|
43
43
|
|
|
44
44
|
## Enforcement Outcome
|
|
45
45
|
|
|
@@ -2,12 +2,12 @@
|
|
|
2
2
|
paths:
|
|
3
3
|
- "**/*.cs"
|
|
4
4
|
- "**/*.csproj"
|
|
5
|
-
description: C#-specific toolchain and coding standards (
|
|
5
|
+
description: C#-specific toolchain and coding standards (xUnit).
|
|
6
6
|
---
|
|
7
7
|
|
|
8
8
|
# C# Code Standards
|
|
9
9
|
|
|
10
|
-
This rule file summarizes the C#-specific policies for this repository. It targets
|
|
10
|
+
This rule file summarizes the C#-specific policies for this repository. It targets a host-neutral .NET foundation: xUnit, NSubstitute, FluentAssertions, `dotnet build`, the analyzer stack, `TimeProvider`, and uniform coverage thresholds.
|
|
11
11
|
|
|
12
12
|
## Toolchain
|
|
13
13
|
|
|
@@ -26,7 +26,7 @@ Apply these priorities in order when designing or changing code:
|
|
|
26
26
|
|
|
27
27
|
## Module Rigor Tiers
|
|
28
28
|
|
|
29
|
-
Module rigor tiers (T1–T4) and the uniform-versus-tier-dependent gate matrix are defined in `.claude/rules/quality-tiers.md
|
|
29
|
+
Module rigor tiers (T1–T4) and the uniform-versus-tier-dependent gate matrix are defined in `.claude/rules/quality-tiers.md` and apply only when `quality-tiers.yml` exists at the repository root; in that case every project must be classified in it. A repository without `quality-tiers.yml` has not adopted tiers, and the tier requirements do not apply.
|
|
30
30
|
|
|
31
31
|
## Mandatory Toolchain Loop
|
|
32
32
|
|
|
@@ -20,10 +20,11 @@ Every unit test must satisfy all five of these properties:
|
|
|
20
20
|
|
|
21
21
|
## Coverage Requirements
|
|
22
22
|
|
|
23
|
+
- Threshold precedence: when the repository's root `CLAUDE.md` states line or branch coverage thresholds, those thresholds govern. The 85% line and 75% branch figures are defaults that apply only when the root `CLAUDE.md` states none. This precedence applies to every restatement of these figures in other rule files, agents, and skills. Each metric falls back independently: when the root `CLAUDE.md` states only a line threshold or only a branch threshold, the stated threshold governs that metric and the default governs the other.
|
|
23
24
|
- **Line coverage must remain >= 85% across all tiers (T1–T4).**
|
|
24
25
|
- **Branch coverage must remain >= 75% across all tiers (T1–T4) for languages whose coverage tooling measures branch coverage.** PowerShell (Pester) and bash (kcov) are the exceptions: neither tool measures branch coverage in any output format, so only the line threshold applies to them and there is no branch-coverage gate. This is a threshold exemption only; PowerShell and bash production files remain in the coverage denominator under the Coverage Exclusion Policy below.
|
|
25
26
|
- Code changes or refactors must not reduce coverage for the lines that were changed.
|
|
26
|
-
- Tier-specific lower coverage thresholds are not used
|
|
27
|
+
- Tier-specific lower coverage thresholds are not used. See `.claude/rules/quality-tiers.md` for the full tier system, which applies only when `quality-tiers.yml` exists at the repository root.
|
|
27
28
|
- Coverage is a supporting metric, not the sole quality gate. Untested critical behavior is not acceptable even if the overall percentage looks good.
|
|
28
29
|
- Configure coverage tooling to exclude test files (e.g., `tests/`) so metrics reflect application code, not tests.
|
|
29
30
|
- Type-only / interface-only modules with no executable behavior may be omitted from coverage measurement. Examples: Python `Protocol`-only modules consumed only under `TYPE_CHECKING`, TypeScript interface/type-only files, and C# interface-only files. Such modules legitimately report 0% executable coverage and may be excluded from measurement. This is a clarification only; it does not lower any coverage threshold.
|
|
@@ -86,7 +87,7 @@ Colocation — placing test files alongside production source files in `src/` or
|
|
|
86
87
|
|
|
87
88
|
## Test Categories
|
|
88
89
|
|
|
89
|
-
The following test categories apply across the repository, with tier-dependent obligations per `.claude/rules/quality-tiers.md
|
|
90
|
+
The following test categories apply across the repository, with tier-dependent obligations per `.claude/rules/quality-tiers.md`; those tier-dependent obligations apply only when `quality-tiers.yml` exists at the repository root:
|
|
90
91
|
|
|
91
92
|
- **Unit tests** — required for all tiers (T1–T4). Cover single units of behavior in isolation.
|
|
92
93
|
- **Property-based tests** — required for T1 and T2 modules: at least one property test per pure function. Use `fast-check` (TypeScript) or `hypothesis` (Python) where applicable.
|