@danmoisan/drm-copilot-mcp 1.1.15 → 1.1.17

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.
Files changed (71) hide show
  1. package/out/mcp-server.js +639 -27
  2. package/package.json +1 -1
  3. package/resources/claude-customizations/.claude/agents/parallel-orchestrator.md +12 -6
  4. package/resources/claude-customizations/.claude/agents/powershell-typed-engineer.md +4 -5
  5. package/resources/claude-customizations/.claude/agents/python-typed-engineer.md +3 -3
  6. package/resources/claude-customizations/.claude/hooks/enforce-batch-budget-route.ps1 +139 -0
  7. package/resources/claude-customizations/.claude/hooks/enforce-epic-merge-gate-resolution.ps1 +221 -0
  8. package/resources/claude-customizations/.claude/hooks/enforce-epic-merge-gate.ps1 +42 -66
  9. package/resources/claude-customizations/.claude/hooks/enforce-epic-wave-barrier.ps1 +58 -10
  10. package/resources/claude-customizations/.claude/hooks/enforce-epic-worktree-removal-gate-resolution.ps1 +144 -0
  11. package/resources/claude-customizations/.claude/hooks/enforce-epic-worktree-removal-gate.ps1 +36 -47
  12. package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate-epic-scope.ps1 +179 -27
  13. package/resources/claude-customizations/.claude/hooks/enforce-orchestration-preimplementation-gate.ps1 +21 -38
  14. package/resources/claude-customizations/.claude/hooks/enforce-parallel-abandon-gate.ps1 +4 -4
  15. package/resources/claude-customizations/.claude/hooks/enforce-parallel-cohort-barrier.ps1 +58 -10
  16. package/resources/claude-customizations/.claude/hooks/enforce-parallel-drift-gate.ps1 +59 -9
  17. package/resources/claude-customizations/.claude/hooks/enforce-parallel-worktree-removal-gate.ps1 +114 -37
  18. package/resources/claude-customizations/.claude/hooks/enforce-powershell-batch-budget.ps1 +95 -66
  19. package/resources/claude-customizations/.claude/hooks/enforce-python-batch-budget.ps1 +99 -64
  20. package/resources/claude-customizations/.claude/lib/bash/abandon-parallel-item.sh +176 -0
  21. package/resources/claude-customizations/.claude/lib/blast-radius/BlastRadiusConflict.psm1 +193 -14
  22. package/resources/claude-customizations/.claude/lib/blast-radius/BlastRadiusGlob.psm1 +51 -28
  23. package/resources/claude-customizations/.claude/lib/blast-radius/BlastRadiusScheduling.psm1 +5 -8
  24. package/resources/claude-customizations/.claude/lib/parallel-drift/Invoke-ParallelDriftDetection.ps1 +336 -0
  25. package/resources/claude-customizations/.claude/lib/parallel-drift/ParallelDrift.psm1 +467 -0
  26. package/resources/claude-customizations/.claude/lib/parallel-drift/ParallelDriftHalt.psm1 +388 -0
  27. package/resources/claude-customizations/.claude/lib/worktree-resolution/EpicScopeResolution.psm1 +53 -32
  28. package/resources/claude-customizations/.claude/lib/worktree-resolution/WorktreeItemResolution.psm1 +19 -4
  29. package/resources/claude-customizations/.claude/lib/worktree-resolution/WorktreeRunResolution.psm1 +497 -0
  30. package/resources/claude-customizations/.claude/rules/parallel-orchestration.md +21 -0
  31. package/resources/claude-customizations/.claude/rules/powershell.md +3 -3
  32. package/resources/claude-customizations/.claude/skills/epic-orchestrate/SKILL.md +2 -0
  33. package/resources/claude-customizations/.claude/skills/invoke-csharp-engineer/SKILL.md +4 -0
  34. package/resources/claude-customizations/.claude/skills/invoke-powershell-engineer/SKILL.md +7 -4
  35. package/resources/claude-customizations/.claude/skills/invoke-python-engineer/SKILL.md +6 -3
  36. package/resources/claude-customizations/.claude/skills/orchestrate/SKILL.md +3 -1
  37. package/resources/claude-customizations/.claude/skills/parallel-orchestrate/SKILL.md +32 -18
  38. package/resources/claude-customizations/.claude/skills/parallel-remove/SKILL.md +10 -10
  39. package/resources/claude-customizations/.claude/skills/powershell-change-budget-router/SKILL.md +6 -6
  40. package/resources/claude-customizations/.claude/skills/python-change-budget-router/SKILL.md +11 -35
  41. package/resources/claude-customizations/pack-manifests/core.json +8 -0
  42. package/resources/codex-and-agents-customizations/.agents/skills/invoke-powershell-engineer/SKILL.md +1 -2
  43. package/resources/codex-and-agents-customizations/.agents/skills/invoke-python-engineer/SKILL.md +2 -3
  44. package/resources/codex-and-agents-customizations/.agents/skills/powershell/SKILL.md +1 -2
  45. package/resources/codex-and-agents-customizations/.agents/skills/python-change-budget-router/SKILL.md +10 -34
  46. package/resources/codex-and-agents-customizations/.codex/agents/powershell-typed-engineer-c1.toml +2 -3
  47. package/resources/codex-and-agents-customizations/.codex/agents/powershell-typed-engineer-c2.toml +2 -3
  48. package/resources/codex-and-agents-customizations/.codex/agents/powershell-typed-engineer-c3-elevated.toml +2 -3
  49. package/resources/codex-and-agents-customizations/.codex/agents/powershell-typed-engineer-c3.toml +2 -3
  50. package/resources/codex-and-agents-customizations/.codex/agents/powershell-typed-engineer-c4.toml +2 -3
  51. package/resources/codex-and-agents-customizations/.codex/agents/powershell-typed-engineer.toml +2 -3
  52. package/resources/codex-and-agents-customizations/.codex/agents/python-orchestrator.toml +2 -2
  53. package/resources/codex-and-agents-customizations/.codex/agents/python-typed-engineer-c1.toml +3 -3
  54. package/resources/codex-and-agents-customizations/.codex/agents/python-typed-engineer-c2.toml +3 -3
  55. package/resources/codex-and-agents-customizations/.codex/agents/python-typed-engineer-c3-elevated.toml +3 -3
  56. package/resources/codex-and-agents-customizations/.codex/agents/python-typed-engineer-c3.toml +3 -3
  57. package/resources/codex-and-agents-customizations/.codex/agents/python-typed-engineer-c4.toml +3 -3
  58. package/resources/codex-and-agents-customizations/.codex/agents/python-typed-engineer.toml +3 -3
  59. package/resources/codex-and-agents-customizations/.codex/config.toml +1 -1
  60. package/resources/codex-and-agents-customizations/.codex/hooks/enforce-batch-budget-route.ps1 +139 -0
  61. package/resources/codex-and-agents-customizations/.codex/hooks/enforce-powershell-batch-budget.ps1 +165 -80
  62. package/resources/codex-and-agents-customizations/.codex/hooks/enforce-python-batch-budget.ps1 +169 -79
  63. package/resources/codex-and-agents-customizations/pack-manifests/core.json +1 -0
  64. package/resources/customizations/.github/agents/powershell-orchestrator.agent.md +7 -7
  65. package/resources/customizations/.github/agents/powershell-typed-engineer.agent.md +8 -10
  66. package/resources/customizations/.github/agents/python-orchestrator.agent.md +4 -4
  67. package/resources/customizations/.github/agents/python-typed-engineer.agent.md +7 -8
  68. package/resources/customizations/.github/prompts/orchestrate-powershell-work.prompt.md +2 -2
  69. package/resources/customizations/.github/prompts/orchestrate-python-work.prompt.md +3 -3
  70. package/resources/customizations/.github/skills/powershell-change-budget-router/SKILL.md +3 -3
  71. package/resources/powershell/PoshQC/settings/pester.runsettings.psd1 +12 -0
@@ -29,7 +29,7 @@ Migration contract:
29
29
 
30
30
  ---
31
31
  name: python-typed-engineer
32
- description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 3-production + 3-test per-batch budget, and zero-regression quality gates.
32
+ description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 1-3 production-file direct-mode budget with routing to the orchestrated large path above it, and zero-regression quality gates.
33
33
  tools:
34
34
  - Read
35
35
  - Write
@@ -65,7 +65,7 @@ Language standards and toolchain are defined in `.agents/skills/python/SKILL.md`
65
65
  Follow the phased workflow defined by the preloaded skills:
66
66
 
67
67
  1. **Policy compliance** — apply `policy-compliance-order` to load mandatory repo policies before any change.
68
- 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope, select small vs large path, and enforce the 3 production + 3 test per-batch cap.
68
+ 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope and select direct mode (1-3 production files) or, for more than 3 production files, large-path escalation through `.codex/prompts/orchestrate-work.md`. The large path has no production-file cap, and test files are not counted toward the routing threshold.
69
69
  3. **Plan and baseline** — apply `atomic-plan-contract` for Phase 0 baseline capture and atomic plan structure. Delegate plan authoring to `atomic_planner` when no plan is supplied.
70
70
  4. **Implement in batches** — apply the approved plan. After each batch, run targeted Ruff and Pyright on touched files plus targeted Pytest, and confirm per-file coverage.
71
71
  5. **Final QA gate** — apply `python-qa-gate` to run the full toolchain, enforce zero-regression deltas against the baseline, and produce the required reporting block before declaring completion.
@@ -86,7 +86,7 @@ If the marker is missing or malformed, fail closed to `full-feature`.
86
86
 
87
87
  Stop implementation and return to the user when:
88
88
 
89
- - the scope estimate or an in-flight batch would exceed the 3-production-file cap,
89
+ - the scope estimate exceeds 3 production files in direct mode,
90
90
  - a file is near or would exceed the 500-line limit,
91
91
  - any QA gate delta is non-zero after self-correction,
92
92
  - the toolchain cannot be executed in the current environment (mark the change **unverified**),
@@ -29,7 +29,7 @@ Migration contract:
29
29
 
30
30
  ---
31
31
  name: python-typed-engineer
32
- description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 3-production + 3-test per-batch budget, and zero-regression quality gates.
32
+ description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 1-3 production-file direct-mode budget with routing to the orchestrated large path above it, and zero-regression quality gates.
33
33
  tools:
34
34
  - Read
35
35
  - Write
@@ -65,7 +65,7 @@ Language standards and toolchain are defined in `.agents/skills/python/SKILL.md`
65
65
  Follow the phased workflow defined by the preloaded skills:
66
66
 
67
67
  1. **Policy compliance** — apply `policy-compliance-order` to load mandatory repo policies before any change.
68
- 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope, select small vs large path, and enforce the 3 production + 3 test per-batch cap.
68
+ 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope and select direct mode (1-3 production files) or, for more than 3 production files, large-path escalation through `.codex/prompts/orchestrate-work.md`. The large path has no production-file cap, and test files are not counted toward the routing threshold.
69
69
  3. **Plan and baseline** — apply `atomic-plan-contract` for Phase 0 baseline capture and atomic plan structure. Delegate plan authoring to `atomic_planner` when no plan is supplied.
70
70
  4. **Implement in batches** — apply the approved plan. After each batch, run targeted Ruff and Pyright on touched files plus targeted Pytest, and confirm per-file coverage.
71
71
  5. **Final QA gate** — apply `python-qa-gate` to run the full toolchain, enforce zero-regression deltas against the baseline, and produce the required reporting block before declaring completion.
@@ -86,7 +86,7 @@ If the marker is missing or malformed, fail closed to `full-feature`.
86
86
 
87
87
  Stop implementation and return to the user when:
88
88
 
89
- - the scope estimate or an in-flight batch would exceed the 3-production-file cap,
89
+ - the scope estimate exceeds 3 production files in direct mode,
90
90
  - a file is near or would exceed the 500-line limit,
91
91
  - any QA gate delta is non-zero after self-correction,
92
92
  - the toolchain cannot be executed in the current environment (mark the change **unverified**),
@@ -29,7 +29,7 @@ Migration contract:
29
29
 
30
30
  ---
31
31
  name: python-typed-engineer
32
- description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 3-production + 3-test per-batch budget, and zero-regression quality gates.
32
+ description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 1-3 production-file direct-mode budget with routing to the orchestrated large path above it, and zero-regression quality gates.
33
33
  tools:
34
34
  - Read
35
35
  - Write
@@ -65,7 +65,7 @@ Language standards and toolchain are defined in `.agents/skills/python/SKILL.md`
65
65
  Follow the phased workflow defined by the preloaded skills:
66
66
 
67
67
  1. **Policy compliance** — apply `policy-compliance-order` to load mandatory repo policies before any change.
68
- 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope, select small vs large path, and enforce the 3 production + 3 test per-batch cap.
68
+ 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope and select direct mode (1-3 production files) or, for more than 3 production files, large-path escalation through `.codex/prompts/orchestrate-work.md`. The large path has no production-file cap, and test files are not counted toward the routing threshold.
69
69
  3. **Plan and baseline** — apply `atomic-plan-contract` for Phase 0 baseline capture and atomic plan structure. Delegate plan authoring to `atomic_planner` when no plan is supplied.
70
70
  4. **Implement in batches** — apply the approved plan. After each batch, run targeted Ruff and Pyright on touched files plus targeted Pytest, and confirm per-file coverage.
71
71
  5. **Final QA gate** — apply `python-qa-gate` to run the full toolchain, enforce zero-regression deltas against the baseline, and produce the required reporting block before declaring completion.
@@ -86,7 +86,7 @@ If the marker is missing or malformed, fail closed to `full-feature`.
86
86
 
87
87
  Stop implementation and return to the user when:
88
88
 
89
- - the scope estimate or an in-flight batch would exceed the 3-production-file cap,
89
+ - the scope estimate exceeds 3 production files in direct mode,
90
90
  - a file is near or would exceed the 500-line limit,
91
91
  - any QA gate delta is non-zero after self-correction,
92
92
  - the toolchain cannot be executed in the current environment (mark the change **unverified**),
@@ -29,7 +29,7 @@ Migration contract:
29
29
 
30
30
  ---
31
31
  name: python-typed-engineer
32
- description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 3-production + 3-test per-batch budget, and zero-regression quality gates.
32
+ description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 1-3 production-file direct-mode budget with routing to the orchestrated large path above it, and zero-regression quality gates.
33
33
  tools:
34
34
  - Read
35
35
  - Write
@@ -65,7 +65,7 @@ Language standards and toolchain are defined in `.agents/skills/python/SKILL.md`
65
65
  Follow the phased workflow defined by the preloaded skills:
66
66
 
67
67
  1. **Policy compliance** — apply `policy-compliance-order` to load mandatory repo policies before any change.
68
- 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope, select small vs large path, and enforce the 3 production + 3 test per-batch cap.
68
+ 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope and select direct mode (1-3 production files) or, for more than 3 production files, large-path escalation through `.codex/prompts/orchestrate-work.md`. The large path has no production-file cap, and test files are not counted toward the routing threshold.
69
69
  3. **Plan and baseline** — apply `atomic-plan-contract` for Phase 0 baseline capture and atomic plan structure. Delegate plan authoring to `atomic_planner` when no plan is supplied.
70
70
  4. **Implement in batches** — apply the approved plan. After each batch, run targeted Ruff and Pyright on touched files plus targeted Pytest, and confirm per-file coverage.
71
71
  5. **Final QA gate** — apply `python-qa-gate` to run the full toolchain, enforce zero-regression deltas against the baseline, and produce the required reporting block before declaring completion.
@@ -86,7 +86,7 @@ If the marker is missing or malformed, fail closed to `full-feature`.
86
86
 
87
87
  Stop implementation and return to the user when:
88
88
 
89
- - the scope estimate or an in-flight batch would exceed the 3-production-file cap,
89
+ - the scope estimate exceeds 3 production files in direct mode,
90
90
  - a file is near or would exceed the 500-line limit,
91
91
  - any QA gate delta is non-zero after self-correction,
92
92
  - the toolchain cannot be executed in the current environment (mark the change **unverified**),
@@ -29,7 +29,7 @@ Migration contract:
29
29
 
30
30
  ---
31
31
  name: python-typed-engineer
32
- description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 3-production + 3-test per-batch budget, and zero-regression quality gates.
32
+ description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 1-3 production-file direct-mode budget with routing to the orchestrated large path above it, and zero-regression quality gates.
33
33
  tools:
34
34
  - Read
35
35
  - Write
@@ -65,7 +65,7 @@ Language standards and toolchain are defined in `.agents/skills/python/SKILL.md`
65
65
  Follow the phased workflow defined by the preloaded skills:
66
66
 
67
67
  1. **Policy compliance** — apply `policy-compliance-order` to load mandatory repo policies before any change.
68
- 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope, select small vs large path, and enforce the 3 production + 3 test per-batch cap.
68
+ 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope and select direct mode (1-3 production files) or, for more than 3 production files, large-path escalation through `.codex/prompts/orchestrate-work.md`. The large path has no production-file cap, and test files are not counted toward the routing threshold.
69
69
  3. **Plan and baseline** — apply `atomic-plan-contract` for Phase 0 baseline capture and atomic plan structure. Delegate plan authoring to `atomic_planner` when no plan is supplied.
70
70
  4. **Implement in batches** — apply the approved plan. After each batch, run targeted Ruff and Pyright on touched files plus targeted Pytest, and confirm per-file coverage.
71
71
  5. **Final QA gate** — apply `python-qa-gate` to run the full toolchain, enforce zero-regression deltas against the baseline, and produce the required reporting block before declaring completion.
@@ -86,7 +86,7 @@ If the marker is missing or malformed, fail closed to `full-feature`.
86
86
 
87
87
  Stop implementation and return to the user when:
88
88
 
89
- - the scope estimate or an in-flight batch would exceed the 3-production-file cap,
89
+ - the scope estimate exceeds 3 production files in direct mode,
90
90
  - a file is near or would exceed the 500-line limit,
91
91
  - any QA gate delta is non-zero after self-correction,
92
92
  - the toolchain cannot be executed in the current environment (mark the change **unverified**),
@@ -29,7 +29,7 @@ Migration contract:
29
29
 
30
30
  ---
31
31
  name: python-typed-engineer
32
- description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 3-production + 3-test per-batch budget, and zero-regression quality gates.
32
+ description: Project-scoped worker that implements and verifies Python changes within typed repository boundaries. Applies the Black -> Ruff -> Pyright -> Pytest toolchain, the 1-3 production-file direct-mode budget with routing to the orchestrated large path above it, and zero-regression quality gates.
33
33
  tools:
34
34
  - Read
35
35
  - Write
@@ -65,7 +65,7 @@ Language standards and toolchain are defined in `.agents/skills/python/SKILL.md`
65
65
  Follow the phased workflow defined by the preloaded skills:
66
66
 
67
67
  1. **Policy compliance** — apply `policy-compliance-order` to load mandatory repo policies before any change.
68
- 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope, select small vs large path, and enforce the 3 production + 3 test per-batch cap.
68
+ 2. **Routing and scope** — apply `python-change-budget-router` to estimate scope and select direct mode (1-3 production files) or, for more than 3 production files, large-path escalation through `.codex/prompts/orchestrate-work.md`. The large path has no production-file cap, and test files are not counted toward the routing threshold.
69
69
  3. **Plan and baseline** — apply `atomic-plan-contract` for Phase 0 baseline capture and atomic plan structure. Delegate plan authoring to `atomic_planner` when no plan is supplied.
70
70
  4. **Implement in batches** — apply the approved plan. After each batch, run targeted Ruff and Pyright on touched files plus targeted Pytest, and confirm per-file coverage.
71
71
  5. **Final QA gate** — apply `python-qa-gate` to run the full toolchain, enforce zero-regression deltas against the baseline, and produce the required reporting block before declaring completion.
@@ -86,7 +86,7 @@ If the marker is missing or malformed, fail closed to `full-feature`.
86
86
 
87
87
  Stop implementation and return to the user when:
88
88
 
89
- - the scope estimate or an in-flight batch would exceed the 3-production-file cap,
89
+ - the scope estimate exceeds 3 production files in direct mode,
90
90
  - a file is near or would exceed the 500-line limit,
91
91
  - any QA gate delta is non-zero after self-correction,
92
92
  - the toolchain cannot be executed in the current environment (mark the change **unverified**),
@@ -2,7 +2,7 @@ default_permissions = ":danger-full-access"
2
2
 
3
3
  [mcp_servers.drm-copilot]
4
4
  command = "npx"
5
- args = ["-y", "@danmoisan/drm-copilot-mcp@1.1.15"]
5
+ args = ["-y", "@danmoisan/drm-copilot-mcp@1.1.17"]
6
6
  required = true
7
7
  enabled_tools = [
8
8
  "collect_commit_context",
@@ -0,0 +1,139 @@
1
+ <#
2
+ .SYNOPSIS
3
+ Pure route helpers shared by the batch-budget hooks.
4
+
5
+ .DESCRIPTION
6
+ Defines the functions that read the selected route from orchestrator checkpoint
7
+ text and decide whether that checkpoint selects the uncapped orchestrated large
8
+ path. The file is dot-sourced by the PowerShell and Python batch-budget hooks and
9
+ has no entry point. The Claude and Codex runtime copies of this file are
10
+ byte-identical, and a parity test holds them identical. None of the functions
11
+ reads a file or an environment variable; the checkpoint text is supplied by the
12
+ caller.
13
+
14
+ .NOTES
15
+ Compatible with PowerShell 7+.
16
+ #>
17
+
18
+ function ConvertFrom-BatchBudgetCheckpoint {
19
+ <#
20
+ .SYNOPSIS
21
+ Parses orchestrator checkpoint text into a checkpoint object.
22
+ .DESCRIPTION
23
+ Returns the parsed object only when the text is a JSON object. Null or
24
+ whitespace text, text that is not parseable JSON, and JSON whose root is not
25
+ an object all return $null. Performs no file or environment access.
26
+ .PARAMETER CheckpointText
27
+ Raw text of the orchestrator checkpoint file.
28
+ #>
29
+ [CmdletBinding()]
30
+ [OutputType([psobject])]
31
+ param(
32
+ [AllowNull()]
33
+ [AllowEmptyString()]
34
+ [string] $CheckpointText
35
+ )
36
+
37
+ if ([string]::IsNullOrWhiteSpace($CheckpointText)) {
38
+ return $null
39
+ }
40
+
41
+ try {
42
+ $parsed = ConvertFrom-Json -InputObject $CheckpointText -ErrorAction Stop
43
+ } catch {
44
+ Write-Verbose "Ignoring unparseable orchestrator checkpoint text: $($_.Exception.Message)"
45
+ return $null
46
+ }
47
+
48
+ if ($parsed -is [System.Management.Automation.PSCustomObject]) {
49
+ return $parsed
50
+ }
51
+
52
+ return $null
53
+ }
54
+
55
+ function Get-BatchBudgetSelectedRoute {
56
+ <#
57
+ .SYNOPSIS
58
+ Returns the route selected by an orchestrator checkpoint.
59
+ .DESCRIPTION
60
+ Uses route_id when the checkpoint has that key, otherwise path_selected. The
61
+ value is returned only when it is a non-blank string; every other case,
62
+ including unparseable text, returns an empty string.
63
+ .PARAMETER CheckpointText
64
+ Raw text of the orchestrator checkpoint file.
65
+ #>
66
+ [CmdletBinding()]
67
+ [OutputType([string])]
68
+ param(
69
+ [AllowNull()]
70
+ [AllowEmptyString()]
71
+ [string] $CheckpointText
72
+ )
73
+
74
+ $checkpoint = ConvertFrom-BatchBudgetCheckpoint -CheckpointText $CheckpointText
75
+ if ($null -eq $checkpoint) {
76
+ return ''
77
+ }
78
+
79
+ $propertyNames = @($checkpoint.PSObject.Properties.Name)
80
+ $rawRoute = $null
81
+ if ($propertyNames -contains 'route_id') {
82
+ $rawRoute = $checkpoint.route_id
83
+ } elseif ($propertyNames -contains 'path_selected') {
84
+ $rawRoute = $checkpoint.path_selected
85
+ }
86
+
87
+ if ($rawRoute -is [string] -and -not [string]::IsNullOrWhiteSpace($rawRoute)) {
88
+ return $rawRoute
89
+ }
90
+
91
+ return ''
92
+ }
93
+
94
+ function Test-BatchBudgetLargePathRoute {
95
+ <#
96
+ .SYNOPSIS
97
+ Reports whether an orchestrator checkpoint selects the uncapped large path.
98
+ .DESCRIPTION
99
+ Returns $true only when the checkpoint parses to an object, its selected route
100
+ is large, remediation, or preparation (case-sensitive), next_step is not
101
+ complete, and completed_steps does not contain S12_complete. No input causes
102
+ an exception; any failure returns $false.
103
+ .PARAMETER CheckpointText
104
+ Raw text of the orchestrator checkpoint file.
105
+ #>
106
+ [CmdletBinding()]
107
+ [OutputType([bool])]
108
+ param(
109
+ [AllowNull()]
110
+ [AllowEmptyString()]
111
+ [string] $CheckpointText
112
+ )
113
+
114
+ try {
115
+ $checkpoint = ConvertFrom-BatchBudgetCheckpoint -CheckpointText $CheckpointText
116
+ if ($null -eq $checkpoint) {
117
+ return $false
118
+ }
119
+
120
+ $route = Get-BatchBudgetSelectedRoute -CheckpointText $CheckpointText
121
+ if (-not (@('large', 'remediation', 'preparation') -ccontains $route)) {
122
+ return $false
123
+ }
124
+
125
+ $propertyNames = @($checkpoint.PSObject.Properties.Name)
126
+ if ($propertyNames -contains 'next_step' -and $checkpoint.next_step -is [string] -and $checkpoint.next_step -ceq 'complete') {
127
+ return $false
128
+ }
129
+
130
+ if ($propertyNames -contains 'completed_steps' -and (@($checkpoint.completed_steps) -ccontains 'S12_complete')) {
131
+ return $false
132
+ }
133
+
134
+ return $true
135
+ } catch {
136
+ Write-Verbose "Treating the orchestrator checkpoint as direct mode: $($_.Exception.Message)"
137
+ return $false
138
+ }
139
+ }