oxe-cc 1.2.1 → 1.4.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.
Files changed (281) hide show
  1. package/.cursor/commands/oxe-ask.md +2 -2
  2. package/.cursor/commands/oxe-capabilities.md +2 -2
  3. package/.cursor/commands/oxe-checkpoint.md +2 -2
  4. package/.cursor/commands/oxe-compact.md +2 -2
  5. package/.cursor/commands/oxe-dashboard.md +2 -2
  6. package/.cursor/commands/oxe-debug.md +2 -2
  7. package/.cursor/commands/oxe-discuss.md +2 -2
  8. package/.cursor/commands/oxe-execute.md +5 -2
  9. package/.cursor/commands/oxe-forensics.md +2 -2
  10. package/.cursor/commands/oxe-help.md +2 -2
  11. package/.cursor/commands/oxe-loop.md +2 -2
  12. package/.cursor/commands/oxe-milestone.md +2 -2
  13. package/.cursor/commands/oxe-next.md +2 -2
  14. package/.cursor/commands/oxe-obs.md +2 -2
  15. package/.cursor/commands/oxe-plan-agent.md +2 -2
  16. package/.cursor/commands/oxe-plan.md +2 -2
  17. package/.cursor/commands/oxe-project.md +2 -2
  18. package/.cursor/commands/oxe-quick.md +2 -2
  19. package/.cursor/commands/oxe-research.md +2 -2
  20. package/.cursor/commands/oxe-retro.md +2 -2
  21. package/.cursor/commands/oxe-review-pr.md +2 -2
  22. package/.cursor/commands/oxe-route.md +2 -2
  23. package/.cursor/commands/oxe-scan.md +2 -2
  24. package/.cursor/commands/oxe-security.md +2 -2
  25. package/.cursor/commands/oxe-session.md +2 -2
  26. package/.cursor/commands/oxe-ship.md +2 -2
  27. package/.cursor/commands/oxe-skill.md +2 -2
  28. package/.cursor/commands/oxe-spec.md +2 -2
  29. package/.cursor/commands/oxe-ui-review.md +2 -2
  30. package/.cursor/commands/oxe-ui-spec.md +2 -2
  31. package/.cursor/commands/oxe-update.md +2 -2
  32. package/.cursor/commands/oxe-validate-gaps.md +2 -2
  33. package/.cursor/commands/oxe-verify.md +5 -2
  34. package/.cursor/commands/oxe-workstream.md +2 -2
  35. package/.cursor/commands/oxe.md +2 -2
  36. package/.github/copilot-instructions.md +13 -13
  37. package/.github/prompts/oxe-ask.prompt.md +2 -2
  38. package/.github/prompts/oxe-capabilities.prompt.md +2 -2
  39. package/.github/prompts/oxe-checkpoint.prompt.md +2 -2
  40. package/.github/prompts/oxe-compact.prompt.md +2 -2
  41. package/.github/prompts/oxe-dashboard.prompt.md +2 -2
  42. package/.github/prompts/oxe-debug.prompt.md +2 -2
  43. package/.github/prompts/oxe-discuss.prompt.md +2 -2
  44. package/.github/prompts/oxe-execute.prompt.md +5 -2
  45. package/.github/prompts/oxe-forensics.prompt.md +2 -2
  46. package/.github/prompts/oxe-help.prompt.md +2 -2
  47. package/.github/prompts/oxe-loop.prompt.md +2 -2
  48. package/.github/prompts/oxe-milestone.prompt.md +2 -2
  49. package/.github/prompts/oxe-next.prompt.md +2 -2
  50. package/.github/prompts/oxe-obs.prompt.md +2 -2
  51. package/.github/prompts/oxe-plan-agent.prompt.md +2 -2
  52. package/.github/prompts/oxe-plan.prompt.md +2 -2
  53. package/.github/prompts/oxe-project.prompt.md +2 -2
  54. package/.github/prompts/oxe-quick.prompt.md +2 -2
  55. package/.github/prompts/oxe-research.prompt.md +2 -2
  56. package/.github/prompts/oxe-retro.prompt.md +2 -2
  57. package/.github/prompts/oxe-review-pr.prompt.md +2 -2
  58. package/.github/prompts/oxe-route.prompt.md +2 -2
  59. package/.github/prompts/oxe-scan.prompt.md +2 -2
  60. package/.github/prompts/oxe-security.prompt.md +2 -2
  61. package/.github/prompts/oxe-session.prompt.md +2 -2
  62. package/.github/prompts/oxe-ship.prompt.md +2 -2
  63. package/.github/prompts/oxe-skill.prompt.md +2 -2
  64. package/.github/prompts/oxe-spec.prompt.md +2 -2
  65. package/.github/prompts/oxe-ui-review.prompt.md +2 -2
  66. package/.github/prompts/oxe-ui-spec.prompt.md +2 -2
  67. package/.github/prompts/oxe-update.prompt.md +2 -2
  68. package/.github/prompts/oxe-validate-gaps.prompt.md +2 -2
  69. package/.github/prompts/oxe-verify.prompt.md +5 -2
  70. package/.github/prompts/oxe-workstream.prompt.md +2 -2
  71. package/.github/prompts/oxe.prompt.md +2 -2
  72. package/AGENTS.md +5 -3
  73. package/CHANGELOG.md +72 -10
  74. package/LICENSE +21 -674
  75. package/README.md +631 -535
  76. package/bin/banner.txt +6 -6
  77. package/bin/lib/oxe-agent-install.cjs +69 -69
  78. package/bin/lib/oxe-azure.cjs +1445 -1445
  79. package/bin/lib/oxe-context-engine.cjs +867 -867
  80. package/bin/lib/oxe-dashboard.cjs +76 -28
  81. package/bin/lib/oxe-operational.cjs +2144 -1340
  82. package/bin/lib/oxe-project-health.cjs +483 -1
  83. package/bin/lib/oxe-runtime-semantics.cjs +12 -0
  84. package/bin/oxe-cc.js +554 -152
  85. package/commands/oxe/ask.md +2 -2
  86. package/commands/oxe/capabilities.md +2 -2
  87. package/commands/oxe/checkpoint.md +2 -2
  88. package/commands/oxe/compact.md +2 -2
  89. package/commands/oxe/dashboard.md +2 -2
  90. package/commands/oxe/debug.md +2 -2
  91. package/commands/oxe/discuss.md +2 -2
  92. package/commands/oxe/execute.md +5 -2
  93. package/commands/oxe/forensics.md +2 -2
  94. package/commands/oxe/help.md +2 -2
  95. package/commands/oxe/loop.md +2 -2
  96. package/commands/oxe/milestone.md +2 -2
  97. package/commands/oxe/next.md +2 -2
  98. package/commands/oxe/obs.md +2 -2
  99. package/commands/oxe/oxe.md +2 -2
  100. package/commands/oxe/plan-agent.md +2 -2
  101. package/commands/oxe/plan.md +2 -2
  102. package/commands/oxe/project.md +2 -2
  103. package/commands/oxe/quick.md +2 -2
  104. package/commands/oxe/research.md +2 -2
  105. package/commands/oxe/retro.md +2 -2
  106. package/commands/oxe/review-pr.md +2 -2
  107. package/commands/oxe/route.md +2 -2
  108. package/commands/oxe/scan.md +2 -2
  109. package/commands/oxe/security.md +2 -2
  110. package/commands/oxe/session.md +2 -2
  111. package/commands/oxe/ship.md +2 -2
  112. package/commands/oxe/skill.md +2 -2
  113. package/commands/oxe/spec.md +2 -2
  114. package/commands/oxe/ui-review.md +2 -2
  115. package/commands/oxe/ui-spec.md +2 -2
  116. package/commands/oxe/update.md +2 -2
  117. package/commands/oxe/validate-gaps.md +2 -2
  118. package/commands/oxe/verify.md +5 -2
  119. package/commands/oxe/workstream.md +2 -2
  120. package/lib/runtime/delivery/branch-manager.d.ts +1 -0
  121. package/lib/runtime/delivery/branch-manager.js +7 -0
  122. package/lib/runtime/delivery/ci-checks.js +34 -1
  123. package/lib/runtime/delivery/delivery-records.d.ts +34 -0
  124. package/lib/runtime/delivery/delivery-records.js +48 -0
  125. package/lib/runtime/delivery/index.d.ts +1 -0
  126. package/lib/runtime/delivery/index.js +1 -0
  127. package/lib/runtime/delivery/promotion-pipeline.d.ts +26 -2
  128. package/lib/runtime/delivery/promotion-pipeline.js +111 -14
  129. package/lib/runtime/gate/gate-manager.d.ts +41 -0
  130. package/lib/runtime/gate/gate-manager.js +108 -1
  131. package/lib/runtime/index.d.ts +2 -2
  132. package/lib/runtime/index.js +3 -1
  133. package/lib/runtime/models/gate-decision.d.ts +4 -1
  134. package/lib/runtime/models/workspace.d.ts +3 -0
  135. package/lib/runtime/plugins/capability-adapter.d.ts +12 -0
  136. package/lib/runtime/plugins/capability-adapter.js +204 -0
  137. package/lib/runtime/plugins/capability-matrix.d.ts +5 -0
  138. package/lib/runtime/plugins/capability-matrix.js +48 -17
  139. package/lib/runtime/plugins/index.d.ts +1 -0
  140. package/lib/runtime/plugins/index.js +1 -0
  141. package/lib/runtime/plugins/plugin-abi.d.ts +2 -0
  142. package/lib/runtime/plugins/plugin-manifest.d.ts +1 -1
  143. package/lib/runtime/plugins/plugin-manifest.js +6 -2
  144. package/lib/runtime/plugins/plugin-registry.d.ts +46 -0
  145. package/lib/runtime/plugins/plugin-registry.js +79 -2
  146. package/lib/runtime/policy/policy-engine.d.ts +19 -0
  147. package/lib/runtime/policy/policy-engine.js +76 -4
  148. package/lib/runtime/projection/projection-engine.d.ts +9 -1
  149. package/lib/runtime/projection/projection-engine.js +73 -3
  150. package/lib/runtime/scheduler/multi-agent-coordinator.d.ts +43 -1
  151. package/lib/runtime/scheduler/multi-agent-coordinator.js +151 -39
  152. package/lib/runtime/scheduler/run-journal.d.ts +1 -1
  153. package/lib/runtime/scheduler/scheduler.d.ts +19 -1
  154. package/lib/runtime/scheduler/scheduler.js +258 -13
  155. package/lib/runtime/verification/verification-compiler.d.ts +43 -0
  156. package/lib/runtime/verification/verification-compiler.js +137 -0
  157. package/lib/runtime/verification/verification-manifest.d.ts +9 -0
  158. package/lib/runtime/verification/verification-manifest.js +56 -6
  159. package/lib/runtime/workspace/strategies/ephemeral-container.d.ts +1 -0
  160. package/lib/runtime/workspace/strategies/ephemeral-container.js +4 -0
  161. package/lib/runtime/workspace/strategies/git-worktree.d.ts +1 -0
  162. package/lib/runtime/workspace/strategies/git-worktree.js +2 -0
  163. package/lib/runtime/workspace/strategies/inplace.d.ts +1 -0
  164. package/lib/runtime/workspace/strategies/inplace.js +2 -0
  165. package/lib/runtime/workspace/workspace-manager.d.ts +2 -1
  166. package/lib/sdk/README.md +20 -8
  167. package/lib/sdk/index.cjs +33 -24
  168. package/lib/sdk/index.d.ts +149 -14
  169. package/oxe/templates/ACTIVE-RUN.template.json +32 -32
  170. package/oxe/templates/CAPABILITIES.template.md +7 -7
  171. package/oxe/templates/CAPABILITY.template.md +45 -45
  172. package/oxe/templates/CHECKPOINTS.template.md +7 -7
  173. package/oxe/templates/EXECUTION-RUNTIME.template.md +68 -68
  174. package/oxe/templates/HYPOTHESES.template.md +33 -33
  175. package/oxe/templates/LESSONS-METRICS.template.json +13 -13
  176. package/oxe/templates/NOTES.template.md +16 -16
  177. package/oxe/templates/PLAN-REVIEW.template.md +31 -31
  178. package/oxe/templates/SESSION.template.md +34 -34
  179. package/oxe/templates/SKILL.template.md +26 -26
  180. package/oxe/templates/STATE.md +55 -55
  181. package/oxe/templates/WORKFLOW_AUTHORING.md +18 -18
  182. package/oxe/workflows/ask.md +96 -96
  183. package/oxe/workflows/capabilities.md +25 -25
  184. package/oxe/workflows/dashboard.md +33 -33
  185. package/oxe/workflows/discuss.md +12 -12
  186. package/oxe/workflows/execute.md +14 -0
  187. package/oxe/workflows/help.md +352 -352
  188. package/oxe/workflows/next.md +22 -22
  189. package/oxe/workflows/oxe.md +6 -6
  190. package/oxe/workflows/plan-agent.md +9 -9
  191. package/oxe/workflows/plan.md +51 -20
  192. package/oxe/workflows/quick.md +10 -10
  193. package/oxe/workflows/references/reasoning-discovery.md +28 -28
  194. package/oxe/workflows/references/reasoning-execution.md +29 -29
  195. package/oxe/workflows/references/reasoning-planning.md +32 -32
  196. package/oxe/workflows/references/reasoning-review.md +29 -29
  197. package/oxe/workflows/references/reasoning-status.md +24 -24
  198. package/oxe/workflows/references/robustness-elevation.md +295 -295
  199. package/oxe/workflows/references/workflow-runtime-contracts.json +952 -930
  200. package/oxe/workflows/route.md +16 -16
  201. package/oxe/workflows/session.md +213 -213
  202. package/oxe/workflows/ship.md +142 -142
  203. package/oxe/workflows/skill.md +44 -44
  204. package/oxe/workflows/ui-review.md +36 -36
  205. package/oxe/workflows/verify-audit.md +73 -73
  206. package/oxe/workflows/verify.md +10 -0
  207. package/package.json +92 -92
  208. package/packages/runtime/package.json +16 -15
  209. package/packages/runtime/src/audit/audit-trail.ts +243 -243
  210. package/packages/runtime/src/audit/index.ts +2 -2
  211. package/packages/runtime/src/audit/policy-pack.ts +62 -62
  212. package/packages/runtime/src/compiler/graph-compiler.ts +245 -245
  213. package/packages/runtime/src/compiler/index.ts +1 -1
  214. package/packages/runtime/src/context/context-pack-builder.ts +259 -259
  215. package/packages/runtime/src/context/context-pack-store.ts +197 -197
  216. package/packages/runtime/src/context/context-profiles.ts +60 -60
  217. package/packages/runtime/src/context/index.ts +3 -3
  218. package/packages/runtime/src/decision/decision-engine.ts +174 -174
  219. package/packages/runtime/src/decision/decision-memo.ts +211 -211
  220. package/packages/runtime/src/decision/index.ts +2 -2
  221. package/packages/runtime/src/delivery/branch-manager.ts +91 -84
  222. package/packages/runtime/src/delivery/ci-checks.ts +285 -252
  223. package/packages/runtime/src/delivery/delivery-records.ts +75 -0
  224. package/packages/runtime/src/delivery/index.ts +5 -4
  225. package/packages/runtime/src/delivery/pr-manager.ts +112 -112
  226. package/packages/runtime/src/delivery/promotion-pipeline.ts +334 -180
  227. package/packages/runtime/src/events/bus.ts +92 -92
  228. package/packages/runtime/src/events/catalog.ts +29 -29
  229. package/packages/runtime/src/events/envelope.ts +14 -14
  230. package/packages/runtime/src/events/index.ts +3 -3
  231. package/packages/runtime/src/evidence/evidence-store.ts +130 -130
  232. package/packages/runtime/src/evidence/index.ts +1 -1
  233. package/packages/runtime/src/gate/gate-manager.ts +289 -137
  234. package/packages/runtime/src/gate/index.ts +1 -1
  235. package/packages/runtime/src/index.ts +41 -37
  236. package/packages/runtime/src/models/attempt.ts +19 -19
  237. package/packages/runtime/src/models/evidence.ts +21 -21
  238. package/packages/runtime/src/models/gate-decision.ts +25 -21
  239. package/packages/runtime/src/models/index.ts +8 -8
  240. package/packages/runtime/src/models/run.ts +24 -24
  241. package/packages/runtime/src/models/session.ts +11 -11
  242. package/packages/runtime/src/models/verification-result.ts +10 -10
  243. package/packages/runtime/src/models/work-item.ts +25 -25
  244. package/packages/runtime/src/models/workspace.ts +31 -28
  245. package/packages/runtime/src/plugins/capability-adapter.ts +206 -0
  246. package/packages/runtime/src/plugins/capability-matrix.ts +126 -83
  247. package/packages/runtime/src/plugins/index.ts +5 -4
  248. package/packages/runtime/src/plugins/plugin-abi.ts +97 -95
  249. package/packages/runtime/src/plugins/plugin-manifest.ts +118 -113
  250. package/packages/runtime/src/plugins/plugin-registry.ts +232 -124
  251. package/packages/runtime/src/policy/index.ts +1 -1
  252. package/packages/runtime/src/policy/policy-engine.ts +330 -244
  253. package/packages/runtime/src/projection/index.ts +1 -1
  254. package/packages/runtime/src/projection/projection-engine.ts +328 -249
  255. package/packages/runtime/src/reducers/debug-reducer.ts +36 -36
  256. package/packages/runtime/src/reducers/index.ts +2 -2
  257. package/packages/runtime/src/reducers/run-state-reducer.ts +269 -269
  258. package/packages/runtime/src/scheduler/agent-registry.ts +132 -132
  259. package/packages/runtime/src/scheduler/agent-roles.ts +109 -109
  260. package/packages/runtime/src/scheduler/index.ts +4 -4
  261. package/packages/runtime/src/scheduler/multi-agent-coordinator.ts +521 -333
  262. package/packages/runtime/src/scheduler/run-journal.ts +62 -62
  263. package/packages/runtime/src/scheduler/scheduler.ts +722 -441
  264. package/packages/runtime/src/verification/index.ts +2 -2
  265. package/packages/runtime/src/verification/verification-compiler.ts +436 -225
  266. package/packages/runtime/src/verification/verification-manifest.ts +252 -192
  267. package/packages/runtime/src/workspace/index.ts +5 -5
  268. package/packages/runtime/src/workspace/strategies/ephemeral-container.ts +126 -121
  269. package/packages/runtime/src/workspace/strategies/git-worktree.ts +79 -77
  270. package/packages/runtime/src/workspace/strategies/inplace.ts +38 -35
  271. package/packages/runtime/src/workspace/workspace-manager.ts +16 -15
  272. package/packages/runtime/tsconfig.json +17 -17
  273. package/vscode-extension/.vscodeignore +7 -7
  274. package/vscode-extension/LICENSE +21 -0
  275. package/vscode-extension/oxe-agents-1.0.0.vsix +0 -0
  276. package/vscode-extension/oxe-agents-1.4.0.vsix +0 -0
  277. package/vscode-extension/package.json +184 -184
  278. package/vscode-extension/src/extension.js +310 -310
  279. package/vscode-extension/src/shared/contextLoader.js +137 -137
  280. package/vscode-extension/src/shared/contractBuilder.js +159 -159
  281. package/vscode-extension/src/shared/stateReader.js +101 -101
@@ -1,245 +1,245 @@
1
- import crypto from 'crypto';
2
- import type { WorkspaceStrategy } from '../models/workspace';
3
-
4
- // Mirror of SDK ParsedTask / ParsedSpec / ParsedPlan interfaces
5
- // (avoids a hard dependency on the CJS SDK from TypeScript source)
6
- export interface ParsedTask {
7
- id: string;
8
- title: string;
9
- wave: number | null;
10
- dependsOn: string[];
11
- files: string[];
12
- verifyCommand: string | null;
13
- aceite: string[];
14
- done: boolean;
15
- meta?: Record<string, unknown> | null;
16
- }
17
-
18
- export interface ParsedSpecCriterion {
19
- id: string;
20
- criterion: string;
21
- howToVerify: string;
22
- }
23
-
24
- export interface ParsedSpec {
25
- objective: string | null;
26
- criteria: ParsedSpecCriterion[];
27
- }
28
-
29
- export interface ParsedPlan {
30
- tasks: ParsedTask[];
31
- waves: Record<number, string[]>;
32
- totalTasks: number;
33
- }
34
-
35
- export interface Action {
36
- type: 'read_code' | 'generate_patch' | 'run_tests' | 'run_lint' | 'collect_evidence' | 'custom';
37
- command?: string;
38
- targets?: string[];
39
- }
40
-
41
- export interface VerifyContract {
42
- must_pass: string[];
43
- acceptance_refs: string[];
44
- command: string | null;
45
- }
46
-
47
- export interface NodePolicy {
48
- requires_human_approval: boolean;
49
- max_retries: number;
50
- }
51
-
52
- export interface GraphNode {
53
- id: string;
54
- title: string;
55
- wave: number;
56
- depends_on: string[];
57
- workspace_strategy: WorkspaceStrategy;
58
- mutation_scope: string[];
59
- actions: Action[];
60
- verify: VerifyContract;
61
- policy: NodePolicy;
62
- }
63
-
64
- export interface GraphEdge {
65
- from: string;
66
- to: string;
67
- type: 'dependency' | 'wave_sequence';
68
- }
69
-
70
- export interface Wave {
71
- wave_number: number;
72
- node_ids: string[];
73
- }
74
-
75
- export interface ExecutionGraphMetadata {
76
- compiled_at: string;
77
- plan_hash: string;
78
- spec_hash: string;
79
- node_count: number;
80
- wave_count: number;
81
- }
82
-
83
- export interface ExecutionGraph {
84
- nodes: Map<string, GraphNode>;
85
- edges: GraphEdge[];
86
- waves: Wave[];
87
- metadata: ExecutionGraphMetadata;
88
- }
89
-
90
- export interface CompilerOptions {
91
- default_workspace_strategy?: WorkspaceStrategy;
92
- default_max_retries?: number;
93
- require_approval_for_all?: boolean;
94
- skip_done_tasks?: boolean;
95
- }
96
-
97
- export function compile(
98
- plan: ParsedPlan,
99
- spec: ParsedSpec,
100
- options: CompilerOptions = {}
101
- ): ExecutionGraph {
102
- const {
103
- default_workspace_strategy = 'git_worktree',
104
- default_max_retries = 2,
105
- require_approval_for_all = false,
106
- skip_done_tasks = false,
107
- } = options;
108
-
109
- const nodes = new Map<string, GraphNode>();
110
- const edges: GraphEdge[] = [];
111
- const waveMap = new Map<number, string[]>();
112
-
113
- for (const task of plan.tasks) {
114
- if (skip_done_tasks && task.done) continue;
115
-
116
- const waveNumber = task.wave ?? 1;
117
- const node: GraphNode = {
118
- id: task.id,
119
- title: task.title,
120
- wave: waveNumber,
121
- depends_on: task.dependsOn,
122
- workspace_strategy: default_workspace_strategy,
123
- mutation_scope: task.files,
124
- actions: buildActions(task),
125
- verify: {
126
- must_pass: task.verifyCommand ? ['tests'] : [],
127
- acceptance_refs: task.aceite,
128
- command: task.verifyCommand,
129
- },
130
- policy: {
131
- requires_human_approval: require_approval_for_all,
132
- max_retries: default_max_retries,
133
- },
134
- };
135
-
136
- nodes.set(task.id, node);
137
-
138
- for (const dep of task.dependsOn) {
139
- edges.push({ from: dep, to: task.id, type: 'dependency' });
140
- }
141
-
142
- if (!waveMap.has(waveNumber)) waveMap.set(waveNumber, []);
143
- waveMap.get(waveNumber)!.push(task.id);
144
- }
145
-
146
- const waves: Wave[] = Array.from(waveMap.entries())
147
- .sort(([a], [b]) => a - b)
148
- .map(([wave_number, node_ids]) => ({ wave_number, node_ids }));
149
-
150
- return {
151
- nodes,
152
- edges,
153
- waves,
154
- metadata: {
155
- compiled_at: new Date().toISOString(),
156
- plan_hash: hashObject(plan),
157
- spec_hash: hashObject(spec),
158
- node_count: nodes.size,
159
- wave_count: waves.length,
160
- },
161
- };
162
- }
163
-
164
- export function validateGraph(graph: ExecutionGraph): string[] {
165
- const errors: string[] = [];
166
- const nodeIds = new Set(graph.nodes.keys());
167
-
168
- for (const [id, node] of graph.nodes) {
169
- for (const dep of node.depends_on) {
170
- if (!nodeIds.has(dep)) {
171
- errors.push(`Node ${id} depends on unknown node ${dep}`);
172
- }
173
- }
174
- }
175
-
176
- // Detect cycles using DFS
177
- const visited = new Set<string>();
178
- const inStack = new Set<string>();
179
-
180
- function hasCycle(nodeId: string): boolean {
181
- if (inStack.has(nodeId)) return true;
182
- if (visited.has(nodeId)) return false;
183
- visited.add(nodeId);
184
- inStack.add(nodeId);
185
- const node = graph.nodes.get(nodeId);
186
- if (node) {
187
- for (const dep of node.depends_on) {
188
- if (hasCycle(dep)) return true;
189
- }
190
- }
191
- inStack.delete(nodeId);
192
- return false;
193
- }
194
-
195
- for (const id of nodeIds) {
196
- if (hasCycle(id)) {
197
- errors.push(`Cycle detected involving node ${id}`);
198
- break;
199
- }
200
- }
201
-
202
- return errors;
203
- }
204
-
205
- export function toSerializable(graph: ExecutionGraph): Record<string, unknown> {
206
- return {
207
- nodes: Object.fromEntries(graph.nodes),
208
- edges: graph.edges,
209
- waves: graph.waves,
210
- metadata: graph.metadata,
211
- };
212
- }
213
-
214
- export function fromSerializable(raw: Record<string, unknown>): ExecutionGraph {
215
- const nodes = new Map<string, GraphNode>(
216
- Object.entries(raw.nodes as Record<string, GraphNode>)
217
- );
218
- return {
219
- nodes,
220
- edges: raw.edges as GraphEdge[],
221
- waves: raw.waves as Wave[],
222
- metadata: raw.metadata as ExecutionGraphMetadata,
223
- };
224
- }
225
-
226
- function buildActions(task: ParsedTask): Action[] {
227
- const actions: Action[] = [];
228
- if (task.files.length > 0) {
229
- actions.push({ type: 'read_code', targets: task.files });
230
- }
231
- actions.push({ type: 'generate_patch' });
232
- if (task.verifyCommand) {
233
- actions.push({ type: 'run_tests', command: task.verifyCommand });
234
- }
235
- actions.push({ type: 'collect_evidence' });
236
- return actions;
237
- }
238
-
239
- function hashObject(obj: unknown): string {
240
- return crypto
241
- .createHash('sha256')
242
- .update(JSON.stringify(obj))
243
- .digest('hex')
244
- .slice(0, 12);
245
- }
1
+ import crypto from 'crypto';
2
+ import type { WorkspaceStrategy } from '../models/workspace';
3
+
4
+ // Mirror of SDK ParsedTask / ParsedSpec / ParsedPlan interfaces
5
+ // (avoids a hard dependency on the CJS SDK from TypeScript source)
6
+ export interface ParsedTask {
7
+ id: string;
8
+ title: string;
9
+ wave: number | null;
10
+ dependsOn: string[];
11
+ files: string[];
12
+ verifyCommand: string | null;
13
+ aceite: string[];
14
+ done: boolean;
15
+ meta?: Record<string, unknown> | null;
16
+ }
17
+
18
+ export interface ParsedSpecCriterion {
19
+ id: string;
20
+ criterion: string;
21
+ howToVerify: string;
22
+ }
23
+
24
+ export interface ParsedSpec {
25
+ objective: string | null;
26
+ criteria: ParsedSpecCriterion[];
27
+ }
28
+
29
+ export interface ParsedPlan {
30
+ tasks: ParsedTask[];
31
+ waves: Record<number, string[]>;
32
+ totalTasks: number;
33
+ }
34
+
35
+ export interface Action {
36
+ type: 'read_code' | 'generate_patch' | 'run_tests' | 'run_lint' | 'collect_evidence' | 'custom';
37
+ command?: string;
38
+ targets?: string[];
39
+ }
40
+
41
+ export interface VerifyContract {
42
+ must_pass: string[];
43
+ acceptance_refs: string[];
44
+ command: string | null;
45
+ }
46
+
47
+ export interface NodePolicy {
48
+ requires_human_approval: boolean;
49
+ max_retries: number;
50
+ }
51
+
52
+ export interface GraphNode {
53
+ id: string;
54
+ title: string;
55
+ wave: number;
56
+ depends_on: string[];
57
+ workspace_strategy: WorkspaceStrategy;
58
+ mutation_scope: string[];
59
+ actions: Action[];
60
+ verify: VerifyContract;
61
+ policy: NodePolicy;
62
+ }
63
+
64
+ export interface GraphEdge {
65
+ from: string;
66
+ to: string;
67
+ type: 'dependency' | 'wave_sequence';
68
+ }
69
+
70
+ export interface Wave {
71
+ wave_number: number;
72
+ node_ids: string[];
73
+ }
74
+
75
+ export interface ExecutionGraphMetadata {
76
+ compiled_at: string;
77
+ plan_hash: string;
78
+ spec_hash: string;
79
+ node_count: number;
80
+ wave_count: number;
81
+ }
82
+
83
+ export interface ExecutionGraph {
84
+ nodes: Map<string, GraphNode>;
85
+ edges: GraphEdge[];
86
+ waves: Wave[];
87
+ metadata: ExecutionGraphMetadata;
88
+ }
89
+
90
+ export interface CompilerOptions {
91
+ default_workspace_strategy?: WorkspaceStrategy;
92
+ default_max_retries?: number;
93
+ require_approval_for_all?: boolean;
94
+ skip_done_tasks?: boolean;
95
+ }
96
+
97
+ export function compile(
98
+ plan: ParsedPlan,
99
+ spec: ParsedSpec,
100
+ options: CompilerOptions = {}
101
+ ): ExecutionGraph {
102
+ const {
103
+ default_workspace_strategy = 'git_worktree',
104
+ default_max_retries = 2,
105
+ require_approval_for_all = false,
106
+ skip_done_tasks = false,
107
+ } = options;
108
+
109
+ const nodes = new Map<string, GraphNode>();
110
+ const edges: GraphEdge[] = [];
111
+ const waveMap = new Map<number, string[]>();
112
+
113
+ for (const task of plan.tasks) {
114
+ if (skip_done_tasks && task.done) continue;
115
+
116
+ const waveNumber = task.wave ?? 1;
117
+ const node: GraphNode = {
118
+ id: task.id,
119
+ title: task.title,
120
+ wave: waveNumber,
121
+ depends_on: task.dependsOn,
122
+ workspace_strategy: default_workspace_strategy,
123
+ mutation_scope: task.files,
124
+ actions: buildActions(task),
125
+ verify: {
126
+ must_pass: task.verifyCommand ? ['tests'] : [],
127
+ acceptance_refs: task.aceite,
128
+ command: task.verifyCommand,
129
+ },
130
+ policy: {
131
+ requires_human_approval: require_approval_for_all,
132
+ max_retries: default_max_retries,
133
+ },
134
+ };
135
+
136
+ nodes.set(task.id, node);
137
+
138
+ for (const dep of task.dependsOn) {
139
+ edges.push({ from: dep, to: task.id, type: 'dependency' });
140
+ }
141
+
142
+ if (!waveMap.has(waveNumber)) waveMap.set(waveNumber, []);
143
+ waveMap.get(waveNumber)!.push(task.id);
144
+ }
145
+
146
+ const waves: Wave[] = Array.from(waveMap.entries())
147
+ .sort(([a], [b]) => a - b)
148
+ .map(([wave_number, node_ids]) => ({ wave_number, node_ids }));
149
+
150
+ return {
151
+ nodes,
152
+ edges,
153
+ waves,
154
+ metadata: {
155
+ compiled_at: new Date().toISOString(),
156
+ plan_hash: hashObject(plan),
157
+ spec_hash: hashObject(spec),
158
+ node_count: nodes.size,
159
+ wave_count: waves.length,
160
+ },
161
+ };
162
+ }
163
+
164
+ export function validateGraph(graph: ExecutionGraph): string[] {
165
+ const errors: string[] = [];
166
+ const nodeIds = new Set(graph.nodes.keys());
167
+
168
+ for (const [id, node] of graph.nodes) {
169
+ for (const dep of node.depends_on) {
170
+ if (!nodeIds.has(dep)) {
171
+ errors.push(`Node ${id} depends on unknown node ${dep}`);
172
+ }
173
+ }
174
+ }
175
+
176
+ // Detect cycles using DFS
177
+ const visited = new Set<string>();
178
+ const inStack = new Set<string>();
179
+
180
+ function hasCycle(nodeId: string): boolean {
181
+ if (inStack.has(nodeId)) return true;
182
+ if (visited.has(nodeId)) return false;
183
+ visited.add(nodeId);
184
+ inStack.add(nodeId);
185
+ const node = graph.nodes.get(nodeId);
186
+ if (node) {
187
+ for (const dep of node.depends_on) {
188
+ if (hasCycle(dep)) return true;
189
+ }
190
+ }
191
+ inStack.delete(nodeId);
192
+ return false;
193
+ }
194
+
195
+ for (const id of nodeIds) {
196
+ if (hasCycle(id)) {
197
+ errors.push(`Cycle detected involving node ${id}`);
198
+ break;
199
+ }
200
+ }
201
+
202
+ return errors;
203
+ }
204
+
205
+ export function toSerializable(graph: ExecutionGraph): Record<string, unknown> {
206
+ return {
207
+ nodes: Object.fromEntries(graph.nodes),
208
+ edges: graph.edges,
209
+ waves: graph.waves,
210
+ metadata: graph.metadata,
211
+ };
212
+ }
213
+
214
+ export function fromSerializable(raw: Record<string, unknown>): ExecutionGraph {
215
+ const nodes = new Map<string, GraphNode>(
216
+ Object.entries(raw.nodes as Record<string, GraphNode>)
217
+ );
218
+ return {
219
+ nodes,
220
+ edges: raw.edges as GraphEdge[],
221
+ waves: raw.waves as Wave[],
222
+ metadata: raw.metadata as ExecutionGraphMetadata,
223
+ };
224
+ }
225
+
226
+ function buildActions(task: ParsedTask): Action[] {
227
+ const actions: Action[] = [];
228
+ if (task.files.length > 0) {
229
+ actions.push({ type: 'read_code', targets: task.files });
230
+ }
231
+ actions.push({ type: 'generate_patch' });
232
+ if (task.verifyCommand) {
233
+ actions.push({ type: 'run_tests', command: task.verifyCommand });
234
+ }
235
+ actions.push({ type: 'collect_evidence' });
236
+ return actions;
237
+ }
238
+
239
+ function hashObject(obj: unknown): string {
240
+ return crypto
241
+ .createHash('sha256')
242
+ .update(JSON.stringify(obj))
243
+ .digest('hex')
244
+ .slice(0, 12);
245
+ }
@@ -1 +1 @@
1
- export * from './graph-compiler';
1
+ export * from './graph-compiler';