@x12i/graphenix-executable-format 1.0.0 → 2.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (259) hide show
  1. package/README.md +512 -341
  2. package/dist/api.d.ts +13 -35
  3. package/dist/api.d.ts.map +1 -1
  4. package/dist/api.js +13 -98
  5. package/dist/api.js.map +1 -1
  6. package/dist/constants.d.ts +1 -11
  7. package/dist/constants.d.ts.map +1 -1
  8. package/dist/constants.js +1 -18
  9. package/dist/constants.js.map +1 -1
  10. package/dist/index.js +1 -17
  11. package/dist/index.js.map +1 -1
  12. package/dist/test/executable-format.test.js +316 -289
  13. package/dist/test/executable-format.test.js.map +1 -1
  14. package/dist/test/executable-plan-v2.test.d.ts +2 -0
  15. package/dist/test/executable-plan-v2.test.d.ts.map +1 -0
  16. package/dist/test/executable-plan-v2.test.js +342 -0
  17. package/dist/test/executable-plan-v2.test.js.map +1 -0
  18. package/dist/test/execution-trace-v2.test.d.ts +2 -0
  19. package/dist/test/execution-trace-v2.test.d.ts.map +1 -0
  20. package/dist/test/execution-trace-v2.test.js +411 -0
  21. package/dist/test/execution-trace-v2.test.js.map +1 -0
  22. package/dist/test/phase-1-format.test.d.ts +2 -0
  23. package/dist/test/phase-1-format.test.d.ts.map +1 -0
  24. package/dist/test/phase-1-format.test.js +297 -0
  25. package/dist/test/phase-1-format.test.js.map +1 -0
  26. package/package.json +69 -56
  27. package/dist/adapter/build-graph-execution-request-from-studio-execute.d.ts +0 -6
  28. package/dist/adapter/build-graph-execution-request-from-studio-execute.d.ts.map +0 -1
  29. package/dist/adapter/build-graph-execution-request-from-studio-execute.js +0 -41
  30. package/dist/adapter/build-graph-execution-request-from-studio-execute.js.map +0 -1
  31. package/dist/case-condition/allowed-paths.d.ts +0 -4
  32. package/dist/case-condition/allowed-paths.d.ts.map +0 -1
  33. package/dist/case-condition/allowed-paths.js +0 -74
  34. package/dist/case-condition/allowed-paths.js.map +0 -1
  35. package/dist/case-condition/evaluate-case-condition.d.ts +0 -4
  36. package/dist/case-condition/evaluate-case-condition.d.ts.map +0 -1
  37. package/dist/case-condition/evaluate-case-condition.js +0 -106
  38. package/dist/case-condition/evaluate-case-condition.js.map +0 -1
  39. package/dist/case-condition/select-graph-model-case.d.ts +0 -6
  40. package/dist/case-condition/select-graph-model-case.d.ts.map +0 -1
  41. package/dist/case-condition/select-graph-model-case.js +0 -40
  42. package/dist/case-condition/select-graph-model-case.js.map +0 -1
  43. package/dist/case-condition/select-node-model-case.d.ts +0 -4
  44. package/dist/case-condition/select-node-model-case.d.ts.map +0 -1
  45. package/dist/case-condition/select-node-model-case.js +0 -34
  46. package/dist/case-condition/select-node-model-case.js.map +0 -1
  47. package/dist/case-condition/validate-case-condition.d.ts +0 -5
  48. package/dist/case-condition/validate-case-condition.d.ts.map +0 -1
  49. package/dist/case-condition/validate-case-condition.js +0 -118
  50. package/dist/case-condition/validate-case-condition.js.map +0 -1
  51. package/dist/compile/build-node-execution-units.d.ts +0 -6
  52. package/dist/compile/build-node-execution-units.d.ts.map +0 -1
  53. package/dist/compile/build-node-execution-units.js +0 -77
  54. package/dist/compile/build-node-execution-units.js.map +0 -1
  55. package/dist/compile/compile-executable-plan.d.ts +0 -5
  56. package/dist/compile/compile-executable-plan.d.ts.map +0 -1
  57. package/dist/compile/compile-executable-plan.js +0 -142
  58. package/dist/compile/compile-executable-plan.js.map +0 -1
  59. package/dist/explain/explain-executable-graph-error.d.ts +0 -4
  60. package/dist/explain/explain-executable-graph-error.d.ts.map +0 -1
  61. package/dist/explain/explain-executable-graph-error.js +0 -14
  62. package/dist/explain/explain-executable-graph-error.js.map +0 -1
  63. package/dist/explain/explain-node-inheritance.d.ts +0 -3
  64. package/dist/explain/explain-node-inheritance.d.ts.map +0 -1
  65. package/dist/explain/explain-node-inheritance.js +0 -41
  66. package/dist/explain/explain-node-inheritance.js.map +0 -1
  67. package/dist/fixtures/minimal-executable-graph.d.ts +0 -4
  68. package/dist/fixtures/minimal-executable-graph.d.ts.map +0 -1
  69. package/dist/fixtures/minimal-executable-graph.js +0 -170
  70. package/dist/fixtures/minimal-executable-graph.js.map +0 -1
  71. package/dist/helpers/add-finalizer-node.d.ts +0 -5
  72. package/dist/helpers/add-finalizer-node.d.ts.map +0 -1
  73. package/dist/helpers/add-finalizer-node.js +0 -13
  74. package/dist/helpers/add-finalizer-node.js.map +0 -1
  75. package/dist/helpers/add-task-node.d.ts +0 -5
  76. package/dist/helpers/add-task-node.d.ts.map +0 -1
  77. package/dist/helpers/add-task-node.js +0 -13
  78. package/dist/helpers/add-task-node.js.map +0 -1
  79. package/dist/helpers/connect-task-to-task.d.ts +0 -10
  80. package/dist/helpers/connect-task-to-task.d.ts.map +0 -1
  81. package/dist/helpers/connect-task-to-task.js +0 -23
  82. package/dist/helpers/connect-task-to-task.js.map +0 -1
  83. package/dist/helpers/set-graph-model-config.d.ts +0 -5
  84. package/dist/helpers/set-graph-model-config.d.ts.map +0 -1
  85. package/dist/helpers/set-graph-model-config.js +0 -30
  86. package/dist/helpers/set-graph-model-config.js.map +0 -1
  87. package/dist/helpers/set-node-model-config.d.ts +0 -5
  88. package/dist/helpers/set-node-model-config.d.ts.map +0 -1
  89. package/dist/helpers/set-node-model-config.js +0 -25
  90. package/dist/helpers/set-node-model-config.js.map +0 -1
  91. package/dist/internal/hash.d.ts +0 -4
  92. package/dist/internal/hash.d.ts.map +0 -1
  93. package/dist/internal/hash.js +0 -26
  94. package/dist/internal/hash.js.map +0 -1
  95. package/dist/internal/utils.d.ts +0 -16
  96. package/dist/internal/utils.d.ts.map +0 -1
  97. package/dist/internal/utils.js +0 -80
  98. package/dist/internal/utils.js.map +0 -1
  99. package/dist/migration/migrate-legacy-graph-model-object.d.ts +0 -4
  100. package/dist/migration/migrate-legacy-graph-model-object.d.ts.map +0 -1
  101. package/dist/migration/migrate-legacy-graph-model-object.js +0 -217
  102. package/dist/migration/migrate-legacy-graph-model-object.js.map +0 -1
  103. package/dist/normalize/normalize-executable-graph.d.ts +0 -3
  104. package/dist/normalize/normalize-executable-graph.d.ts.map +0 -1
  105. package/dist/normalize/normalize-executable-graph.js +0 -34
  106. package/dist/normalize/normalize-executable-graph.js.map +0 -1
  107. package/dist/normalize/normalize-model-config.d.ts +0 -4
  108. package/dist/normalize/normalize-model-config.d.ts.map +0 -1
  109. package/dist/normalize/normalize-model-config.js +0 -64
  110. package/dist/normalize/normalize-model-config.js.map +0 -1
  111. package/dist/profile-choice/known-profile-choices.d.ts +0 -10
  112. package/dist/profile-choice/known-profile-choices.d.ts.map +0 -1
  113. package/dist/profile-choice/known-profile-choices.js +0 -19
  114. package/dist/profile-choice/known-profile-choices.js.map +0 -1
  115. package/dist/profile-choice/validate-profile-choice.d.ts +0 -8
  116. package/dist/profile-choice/validate-profile-choice.d.ts.map +0 -1
  117. package/dist/profile-choice/validate-profile-choice.js +0 -55
  118. package/dist/profile-choice/validate-profile-choice.js.map +0 -1
  119. package/dist/resolution/build-deterministic-case-context.d.ts +0 -9
  120. package/dist/resolution/build-deterministic-case-context.d.ts.map +0 -1
  121. package/dist/resolution/build-deterministic-case-context.js +0 -26
  122. package/dist/resolution/build-deterministic-case-context.js.map +0 -1
  123. package/dist/resolution/resolve-graph-model-config.d.ts +0 -12
  124. package/dist/resolution/resolve-graph-model-config.d.ts.map +0 -1
  125. package/dist/resolution/resolve-graph-model-config.js +0 -28
  126. package/dist/resolution/resolve-graph-model-config.js.map +0 -1
  127. package/dist/resolution/resolve-node-ai-plan.d.ts +0 -7
  128. package/dist/resolution/resolve-node-ai-plan.d.ts.map +0 -1
  129. package/dist/resolution/resolve-node-ai-plan.js +0 -64
  130. package/dist/resolution/resolve-node-ai-plan.js.map +0 -1
  131. package/dist/resolution/resolve-node-model-config.d.ts +0 -15
  132. package/dist/resolution/resolve-node-model-config.d.ts.map +0 -1
  133. package/dist/resolution/resolve-node-model-config.js +0 -37
  134. package/dist/resolution/resolve-node-model-config.js.map +0 -1
  135. package/dist/resolution/resolve-node-model-slot.d.ts +0 -7
  136. package/dist/resolution/resolve-node-model-slot.d.ts.map +0 -1
  137. package/dist/resolution/resolve-node-model-slot.js +0 -65
  138. package/dist/resolution/resolve-node-model-slot.js.map +0 -1
  139. package/dist/trace/append-execution-event.d.ts +0 -5
  140. package/dist/trace/append-execution-event.d.ts.map +0 -1
  141. package/dist/trace/append-execution-event.js +0 -9
  142. package/dist/trace/append-execution-event.js.map +0 -1
  143. package/dist/trace/create-execution-trace.d.ts +0 -5
  144. package/dist/trace/create-execution-trace.d.ts.map +0 -1
  145. package/dist/trace/create-execution-trace.js +0 -56
  146. package/dist/trace/create-execution-trace.js.map +0 -1
  147. package/dist/types/case-condition.d.ts +0 -50
  148. package/dist/types/case-condition.d.ts.map +0 -1
  149. package/dist/types/case-condition.js +0 -3
  150. package/dist/types/case-condition.js.map +0 -1
  151. package/dist/types/errors.d.ts +0 -16
  152. package/dist/types/errors.d.ts.map +0 -1
  153. package/dist/types/errors.js +0 -3
  154. package/dist/types/errors.js.map +0 -1
  155. package/dist/types/executable-graph.d.ts +0 -19
  156. package/dist/types/executable-graph.d.ts.map +0 -1
  157. package/dist/types/executable-graph.js +0 -3
  158. package/dist/types/executable-graph.js.map +0 -1
  159. package/dist/types/executable-nodes.d.ts +0 -54
  160. package/dist/types/executable-nodes.d.ts.map +0 -1
  161. package/dist/types/executable-nodes.js +0 -3
  162. package/dist/types/executable-nodes.js.map +0 -1
  163. package/dist/types/executable-plan.d.ts +0 -78
  164. package/dist/types/executable-plan.d.ts.map +0 -1
  165. package/dist/types/executable-plan.js +0 -5
  166. package/dist/types/executable-plan.js.map +0 -1
  167. package/dist/types/executable-profile.d.ts +0 -18
  168. package/dist/types/executable-profile.d.ts.map +0 -1
  169. package/dist/types/executable-profile.js +0 -3
  170. package/dist/types/executable-profile.js.map +0 -1
  171. package/dist/types/execution-trace.d.ts +0 -278
  172. package/dist/types/execution-trace.d.ts.map +0 -1
  173. package/dist/types/execution-trace.js +0 -5
  174. package/dist/types/execution-trace.js.map +0 -1
  175. package/dist/types/execution-unit.d.ts +0 -19
  176. package/dist/types/execution-unit.d.ts.map +0 -1
  177. package/dist/types/execution-unit.js +0 -3
  178. package/dist/types/execution-unit.js.map +0 -1
  179. package/dist/types/index.d.ts +0 -16
  180. package/dist/types/index.d.ts.map +0 -1
  181. package/dist/types/index.js +0 -8
  182. package/dist/types/index.js.map +0 -1
  183. package/dist/types/legacy.d.ts +0 -21
  184. package/dist/types/legacy.d.ts.map +0 -1
  185. package/dist/types/legacy.js +0 -3
  186. package/dist/types/legacy.js.map +0 -1
  187. package/dist/types/model-config.d.ts +0 -80
  188. package/dist/types/model-config.d.ts.map +0 -1
  189. package/dist/types/model-config.js +0 -3
  190. package/dist/types/model-config.js.map +0 -1
  191. package/dist/types/resolution.d.ts +0 -55
  192. package/dist/types/resolution.d.ts.map +0 -1
  193. package/dist/types/resolution.js +0 -3
  194. package/dist/types/resolution.js.map +0 -1
  195. package/dist/types/runtime.d.ts +0 -19
  196. package/dist/types/runtime.d.ts.map +0 -1
  197. package/dist/types/runtime.js +0 -3
  198. package/dist/types/runtime.js.map +0 -1
  199. package/dist/types/studio-execute.d.ts +0 -25
  200. package/dist/types/studio-execute.d.ts.map +0 -1
  201. package/dist/types/studio-execute.js +0 -3
  202. package/dist/types/studio-execute.js.map +0 -1
  203. package/dist/validators/assert-executable-graph.d.ts +0 -3
  204. package/dist/validators/assert-executable-graph.d.ts.map +0 -1
  205. package/dist/validators/assert-executable-graph.js +0 -14
  206. package/dist/validators/assert-executable-graph.js.map +0 -1
  207. package/dist/validators/assert-normalized-executable-graph.d.ts +0 -3
  208. package/dist/validators/assert-normalized-executable-graph.d.ts.map +0 -1
  209. package/dist/validators/assert-normalized-executable-graph.js +0 -14
  210. package/dist/validators/assert-normalized-executable-graph.js.map +0 -1
  211. package/dist/validators/validate-authoring-executable-graph.d.ts +0 -3
  212. package/dist/validators/validate-authoring-executable-graph.d.ts.map +0 -1
  213. package/dist/validators/validate-authoring-executable-graph.js +0 -134
  214. package/dist/validators/validate-authoring-executable-graph.js.map +0 -1
  215. package/dist/validators/validate-authoring-graph.d.ts +0 -2
  216. package/dist/validators/validate-authoring-graph.d.ts.map +0 -1
  217. package/dist/validators/validate-authoring-graph.js +0 -6
  218. package/dist/validators/validate-authoring-graph.js.map +0 -1
  219. package/dist/validators/validate-executable-graph.d.ts +0 -4
  220. package/dist/validators/validate-executable-graph.d.ts.map +0 -1
  221. package/dist/validators/validate-executable-graph.js +0 -9
  222. package/dist/validators/validate-executable-graph.js.map +0 -1
  223. package/dist/validators/validate-executable-plan.d.ts +0 -3
  224. package/dist/validators/validate-executable-plan.d.ts.map +0 -1
  225. package/dist/validators/validate-executable-plan.js +0 -211
  226. package/dist/validators/validate-executable-plan.js.map +0 -1
  227. package/dist/validators/validate-execution-trace.d.ts +0 -4
  228. package/dist/validators/validate-execution-trace.d.ts.map +0 -1
  229. package/dist/validators/validate-execution-trace.js +0 -158
  230. package/dist/validators/validate-execution-trace.js.map +0 -1
  231. package/dist/validators/validate-finalizer-node.d.ts +0 -4
  232. package/dist/validators/validate-finalizer-node.d.ts.map +0 -1
  233. package/dist/validators/validate-finalizer-node.js +0 -36
  234. package/dist/validators/validate-finalizer-node.js.map +0 -1
  235. package/dist/validators/validate-model-config.d.ts +0 -7
  236. package/dist/validators/validate-model-config.d.ts.map +0 -1
  237. package/dist/validators/validate-model-config.js +0 -197
  238. package/dist/validators/validate-model-config.js.map +0 -1
  239. package/dist/validators/validate-normalized-executable-graph.d.ts +0 -3
  240. package/dist/validators/validate-normalized-executable-graph.d.ts.map +0 -1
  241. package/dist/validators/validate-normalized-executable-graph.js +0 -26
  242. package/dist/validators/validate-normalized-executable-graph.js.map +0 -1
  243. package/dist/validators/validate-runtime-object.d.ts +0 -10
  244. package/dist/validators/validate-runtime-object.d.ts.map +0 -1
  245. package/dist/validators/validate-runtime-object.js +0 -63
  246. package/dist/validators/validate-runtime-object.js.map +0 -1
  247. package/dist/validators/validate-studio-execute-request.d.ts +0 -5
  248. package/dist/validators/validate-studio-execute-request.d.ts.map +0 -1
  249. package/dist/validators/validate-studio-execute-request.js +0 -37
  250. package/dist/validators/validate-studio-execute-request.js.map +0 -1
  251. package/dist/validators/validate-task-actions.d.ts +0 -4
  252. package/dist/validators/validate-task-actions.d.ts.map +0 -1
  253. package/dist/validators/validate-task-actions.js +0 -93
  254. package/dist/validators/validate-task-actions.js.map +0 -1
  255. package/dist/validators/validate-task-node.d.ts +0 -6
  256. package/dist/validators/validate-task-node.d.ts.map +0 -1
  257. package/dist/validators/validate-task-node.js +0 -43
  258. package/dist/validators/validate-task-node.js.map +0 -1
  259. package/schema/graphenix-executable-format-1.0.0.schema.json +0 -40
@@ -1,62 +1,55 @@
1
- "use strict";
2
- var __importDefault = (this && this.__importDefault) || function (mod) {
3
- return (mod && mod.__esModule) ? mod : { "default": mod };
4
- };
5
- Object.defineProperty(exports, "__esModule", { value: true });
6
- const strict_1 = __importDefault(require("node:assert/strict"));
7
- const node_test_1 = require("node:test");
8
- const graphenix_core_1 = require("@x12i/graphenix-core");
9
- const api_js_1 = require("../api.js");
10
- const minimal_executable_graph_js_1 = require("../fixtures/minimal-executable-graph.js");
11
- const graphenix_core_2 = require("@x12i/graphenix-core");
12
- const constants_js_1 = require("../constants.js");
1
+ import assert from "node:assert/strict";
2
+ import { describe, it } from "node:test";
3
+ import { validateGraph } from "@x12i/graphenix-core";
4
+ import { assertExecutableGraph, validateExecutableGraph, validateStudioExecuteRequest, validateRuntimeObject, buildGraphExecutionRequestFromStudioExecute, resolveNodeAiPlan, explainNodeInheritance, resolveNodeModelSlot, normalizeExecutableGraph, validateCaseCondition, evaluateCaseCondition, isProfileChoiceKeyFormat, isKnownProfileChoice, buildDeterministicCaseContext, compileExecutablePlan, validateExecutablePlan, validateAuthoringGraph, createExecutionTrace, appendExecutionEvent, validateExecutionTrace, buildRuntimeObject, createMinimalExecutableGraph, createPlainGraphenixGraph, migrateLegacyGraphModelObjectToGraphenixExecutable, validateAuthoringExecutableGraph } from "../api.js";
5
+ import { EXECUTABLE_PROFILE_NAMESPACE } from "@x12i/graphenix-executable-contracts";
13
6
  function setGraphModelConfig(doc, modelConfig) {
14
7
  const next = structuredClone(doc);
15
- const ext = next.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
8
+ const ext = next.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
16
9
  ext.modelConfig = modelConfig;
17
10
  return next;
18
11
  }
19
- (0, node_test_1.describe)("graphenix base validation", () => {
20
- (0, node_test_1.it)("valid executable graph passes Graphenix validateGraph()", () => {
21
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
22
- const result = (0, graphenix_core_1.validateGraph)(doc);
23
- strict_1.default.equal(result.valid, true);
12
+ describe("graphenix base validation", () => {
13
+ it("valid executable graph passes Graphenix validateGraph()", () => {
14
+ const doc = createMinimalExecutableGraph();
15
+ const result = validateGraph(doc);
16
+ assert.equal(result.valid, true);
24
17
  });
25
18
  });
26
- (0, node_test_1.describe)("executable profile validation", () => {
27
- (0, node_test_1.it)("valid executable graph passes assertExecutableGraph()", () => {
28
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
29
- strict_1.default.doesNotThrow(() => (0, api_js_1.assertExecutableGraph)(doc));
30
- });
31
- (0, node_test_1.it)("plain Graphenix graph without executable profile fails", () => {
32
- const doc = (0, minimal_executable_graph_js_1.createPlainGraphenixGraph)();
33
- const result = (0, api_js_1.validateExecutableGraph)(doc);
34
- strict_1.default.equal(result.valid, false);
35
- strict_1.default.ok(result.errors.some((e) => e.code === "EXECUTABLE_PROFILE_MISSING"));
36
- });
37
- (0, node_test_1.it)("graph-level modelConfig is required", () => {
38
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
39
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
19
+ describe("executable profile validation", () => {
20
+ it("valid executable graph passes assertExecutableGraph()", () => {
21
+ const doc = createMinimalExecutableGraph();
22
+ assert.doesNotThrow(() => assertExecutableGraph(doc));
23
+ });
24
+ it("plain Graphenix graph without executable profile fails", () => {
25
+ const doc = createPlainGraphenixGraph();
26
+ const result = validateExecutableGraph(doc);
27
+ assert.equal(result.valid, false);
28
+ assert.ok(result.errors.some((e) => e.code === "EXECUTABLE_PROFILE_MISSING"));
29
+ });
30
+ it("graph-level modelConfig is required", () => {
31
+ const doc = createMinimalExecutableGraph();
32
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
40
33
  delete ext.modelConfig;
41
- const result = (0, api_js_1.validateExecutableGraph)(doc);
42
- strict_1.default.equal(result.valid, false);
43
- strict_1.default.ok(result.errors.some((e) => e.code === "GRAPH_MODEL_CONFIG_MISSING"));
34
+ const result = validateExecutableGraph(doc);
35
+ assert.equal(result.valid, false);
36
+ assert.ok(result.errors.some((e) => e.code === "GRAPH_MODEL_CONFIG_MISSING"));
44
37
  });
45
38
  });
46
- (0, node_test_1.describe)("model inheritance", () => {
47
- (0, node_test_1.it)("node with no modelConfig inherits all slots", () => {
48
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
49
- const plan = (0, api_js_1.resolveNodeAiPlan)(doc, "node:professional-answer");
50
- strict_1.default.equal(plan.slots.preActionModel.inherited, true);
51
- strict_1.default.equal(plan.slots.skillModel.inherited, true);
52
- strict_1.default.equal(plan.slots.postActionModel.inherited, true);
53
- strict_1.default.match((0, api_js_1.explainNodeInheritance)(plan), /graph case default/);
54
- });
55
- (0, node_test_1.it)("node may override only skillModel", () => {
56
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
39
+ describe("model inheritance", () => {
40
+ it("node with no modelConfig inherits all slots", () => {
41
+ const doc = createMinimalExecutableGraph();
42
+ const plan = resolveNodeAiPlan(doc, "node:professional-answer");
43
+ assert.equal(plan.slots.preActionModel.inherited, true);
44
+ assert.equal(plan.slots.skillModel.inherited, true);
45
+ assert.equal(plan.slots.postActionModel.inherited, true);
46
+ assert.match(explainNodeInheritance(plan), /graph case default/);
47
+ });
48
+ it("node may override only skillModel", () => {
49
+ const doc = createMinimalExecutableGraph();
57
50
  const taskNode = doc.graph.nodes.find((n) => n.id === "node:professional-answer");
58
51
  const params = taskNode.parameters;
59
- strict_1.default.ok(params && params.nodeType === "task");
52
+ assert.ok(params && params.nodeType === "task");
60
53
  taskNode.parameters = {
61
54
  ...params,
62
55
  taskConfiguration: {
@@ -67,14 +60,14 @@ function setGraphModelConfig(doc, modelConfig) {
67
60
  }
68
61
  }
69
62
  };
70
- const plan = (0, api_js_1.resolveNodeAiPlan)(doc, "node:professional-answer");
71
- strict_1.default.equal(plan.slots.skillModel.inherited, false);
72
- strict_1.default.equal(plan.slots.preActionModel.inherited, true);
63
+ const plan = resolveNodeAiPlan(doc, "node:professional-answer");
64
+ assert.equal(plan.slots.skillModel.inherited, false);
65
+ assert.equal(plan.slots.preActionModel.inherited, true);
73
66
  });
74
67
  });
75
- (0, node_test_1.describe)("model fallback", () => {
76
- (0, node_test_1.it)("fallback uses graph same-slot only", () => {
77
- const resolved = (0, api_js_1.resolveNodeModelSlot)({
68
+ describe("model fallback", () => {
69
+ it("fallback uses graph same-slot only", () => {
70
+ const resolved = resolveNodeModelSlot({
78
71
  slot: "skillModel",
79
72
  graphSelection: { kind: "profileChoice", key: "vol/default" },
80
73
  nodeSelection: {
@@ -95,33 +88,33 @@ function setGraphModelConfig(doc, modelConfig) {
95
88
  graphCaseId: "default",
96
89
  nodeId: "node:test"
97
90
  });
98
- strict_1.default.equal(resolved.source, "fallbackToGraphDefault");
99
- strict_1.default.equal(resolved.selected.kind === "profileChoice" ? resolved.selected.key : "", "vol/default");
91
+ assert.equal(resolved.source, "fallbackToGraphDefault");
92
+ assert.equal(resolved.selected.kind === "profileChoice" ? resolved.selected.key : "", "vol/default");
100
93
  });
101
- (0, node_test_1.it)("fallback does not use runtime or request model defaults", () => {
102
- const runtime = (0, api_js_1.validateRuntimeObject)({
94
+ it("fallback does not use runtime or request model defaults", () => {
95
+ const runtime = validateRuntimeObject({
103
96
  jobId: "job-1",
104
97
  job: { id: "job-1", jobId: "job-1" },
105
98
  graphDefaultModel: { kind: "profileChoice", key: "cheap/default" }
106
99
  });
107
- strict_1.default.equal(runtime.valid, false);
100
+ assert.equal(runtime.valid, false);
108
101
  });
109
102
  });
110
- (0, node_test_1.describe)("studio adapter", () => {
111
- (0, node_test_1.it)("studio request with graphDefaultModel fails", () => {
112
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
113
- const result = (0, api_js_1.validateStudioExecuteRequest)({
103
+ describe("studio adapter", () => {
104
+ it("studio request with graphDefaultModel fails", () => {
105
+ const doc = createMinimalExecutableGraph();
106
+ const result = validateStudioExecuteRequest({
114
107
  mode: "graph",
115
108
  jobId: "job-1",
116
109
  graph: doc,
117
110
  graphDefaultModel: {}
118
111
  });
119
- strict_1.default.equal(result.valid, false);
120
- strict_1.default.ok(result.errors.some((e) => e.code === "STUDIO_GRAPH_DEFAULT_MODEL_FORBIDDEN"));
112
+ assert.equal(result.valid, false);
113
+ assert.ok(result.errors.some((e) => e.code === "STUDIO_GRAPH_DEFAULT_MODEL_FORBIDDEN"));
121
114
  });
122
- (0, node_test_1.it)("studio adapter outputs compiled { plan, runtime }", () => {
123
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
124
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
115
+ it("studio adapter outputs compiled { plan, runtime }", () => {
116
+ const doc = createMinimalExecutableGraph();
117
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
125
118
  ext.modelConfig = {
126
119
  version: "graph-model-config/v1",
127
120
  default: {
@@ -139,87 +132,121 @@ function setGraphModelConfig(doc, modelConfig) {
139
132
  },
140
133
  openrouterApiKey: "secret-should-not-copy"
141
134
  };
142
- const execution = (0, api_js_1.buildGraphExecutionRequestFromStudioExecute)(request, {
135
+ const execution = buildGraphExecutionRequestFromStudioExecute(request, {
143
136
  agentId: "agent-1"
144
137
  });
145
- strict_1.default.equal(execution.runtime.jobId, "job-123");
146
- strict_1.default.equal(execution.plan.source.graphId, doc.id);
147
- strict_1.default.equal(execution.plan.format, "x12i.graphenix.executable-plan/v1");
148
- strict_1.default.equal("openrouterApiKey" in execution.runtime, false);
149
- strict_1.default.equal("openrouterApiKey" in execution.plan, false);
150
- const profile = execution.plan.graph.graph.metadata?.extensions?.[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
151
- strict_1.default.equal(profile?.modelConfig?.cases?.[0]?.id, "default");
152
- strict_1.default.equal((0, api_js_1.validateExecutablePlan)(execution.plan).valid, true);
138
+ assert.equal(execution.runtime.jobId, "job-123");
139
+ assert.equal(execution.plan.source.graphId, doc.id);
140
+ assert.equal(execution.plan.format, "graphenix.executable-plan/v1");
141
+ assert.equal("openrouterApiKey" in execution.runtime, false);
142
+ assert.equal("openrouterApiKey" in execution.plan, false);
143
+ const profile = execution.plan.graph.graph.metadata?.extensions?.[EXECUTABLE_PROFILE_NAMESPACE];
144
+ assert.equal(profile?.modelConfig?.cases?.[0]?.id, "default");
145
+ assert.equal(validateExecutablePlan(execution.plan).valid, true);
153
146
  });
154
147
  });
155
- (0, node_test_1.describe)("runtime validation", () => {
156
- (0, node_test_1.it)("credentials are never copied into runtime", () => {
157
- const result = (0, api_js_1.validateRuntimeObject)({
148
+ describe("runtime validation", () => {
149
+ it("credentials are never copied into runtime", () => {
150
+ const result = validateRuntimeObject({
158
151
  jobId: "job-1",
159
152
  job: { id: "job-1", jobId: "job-1" },
160
153
  credentials: { token: "x" }
161
154
  });
162
- strict_1.default.equal(result.valid, false);
155
+ assert.equal(result.valid, false);
163
156
  });
164
- (0, node_test_1.it)("runtime modelConfig is rejected", () => {
165
- const result = (0, api_js_1.validateRuntimeObject)({
157
+ it("runtime modelConfig is rejected", () => {
158
+ const result = validateRuntimeObject({
166
159
  jobId: "job-1",
167
160
  job: { id: "job-1", jobId: "job-1" },
168
161
  modelConfig: {}
169
162
  });
170
- strict_1.default.equal(result.valid, false);
163
+ assert.equal(result.valid, false);
171
164
  });
172
165
  });
173
- (0, node_test_1.describe)("migration", () => {
174
- (0, node_test_1.it)("legacy graph migrates into valid Graphenix executable document", () => {
175
- const migrated = (0, api_js_1.migrateLegacyGraphModelObjectToGraphenixExecutable)({
166
+ describe("legacy migration CRS-001", () => {
167
+ it("flat exellix graph migrates into valid authoring document", () => {
168
+ const migrated = migrateLegacyGraphModelObjectToGraphenixExecutable({
176
169
  id: "graph:legacy",
177
170
  version: "0.1.0",
178
171
  nodes: [
179
172
  {
180
173
  id: "node:a",
181
- kind: "task",
182
- skillKey: "demo"
174
+ type: "task",
175
+ skillKey: "professional-answer",
176
+ conditions: {
177
+ jsonConditions: { path: "runtime.input.ready", op: "eq", value: true }
178
+ },
179
+ smartInput: { paths: ["runtime.input.question"] },
180
+ taskKnowledge: ["kb:faq"]
181
+ },
182
+ {
183
+ id: "node:finalizer",
184
+ type: "finalizer",
185
+ finalizerType: "single-output",
186
+ config: { from: "node:a" }
183
187
  }
184
188
  ],
185
- edges: [],
189
+ edges: [{ from: "node:a", to: "node:finalizer" }],
186
190
  modelConfig: {
187
191
  version: "graph-model-config/v1",
188
192
  cases: [
189
193
  {
190
- id: "default",
191
194
  modelConfig: {
192
- preActionModel: { kind: "profile", profile: "economy" },
193
- skillModel: { kind: "profile", profile: "balanced" },
194
- postActionModel: { kind: "profile", profile: "economy" }
195
+ preActionModel: "cheap",
196
+ skillModel: "balanced",
197
+ postActionModel: "deep"
195
198
  }
196
199
  }
197
200
  ]
198
- }
201
+ },
202
+ metadata: {
203
+ graphEntry: {
204
+ dataFilters: {
205
+ version: "exellix.structured-data-filters/v1",
206
+ when: { path: "runtime.input.tenant", op: "exists" }
207
+ }
208
+ }
209
+ },
210
+ jobKnowledge: ["kb:job"]
199
211
  });
200
- strict_1.default.equal(migrated.formatVersion, graphenix_core_2.GRAPHENIX_FORMAT_VERSION);
201
- strict_1.default.doesNotThrow(() => (0, api_js_1.assertExecutableGraph)(migrated));
212
+ assert.equal(migrated.id, "graph:legacy");
213
+ assert.equal(migrated.graph.nodes.length, 2);
214
+ assert.equal(migrated.graph.nodes[0]?.kind, "task");
215
+ assert.equal((migrated.graph.nodes[0]?.parameters).skillKey, "professional-answer");
216
+ const conditions = (migrated.graph.nodes[0]?.parameters)
217
+ .conditions;
218
+ assert.ok(Array.isArray(conditions.runWhen));
219
+ const smartInput = (migrated.graph.nodes[0]?.parameters)
220
+ .smartInput;
221
+ assert.deepEqual(smartInput?.paths, [{ path: "runtime.input.question" }]);
222
+ const profile = migrated.graph.metadata?.extensions?.["graphenix.executable/v1"];
223
+ const triplet = profile?.modelConfig?.cases?.[0]?.modelConfig;
224
+ assert.equal(triplet?.preActionModel?.kind, "profileChoice");
225
+ assert.equal(triplet?.preActionModel?.key, "cheap/default");
226
+ assert.equal(triplet?.skillModel?.key, "vol/default");
227
+ assert.equal(triplet?.postActionModel?.key, "deep/openai_deep");
228
+ assert.equal(validateAuthoringExecutableGraph(migrated).valid, true);
202
229
  });
203
230
  });
204
- (0, node_test_1.describe)("node kinds", () => {
205
- (0, node_test_1.it)("task nodes must use kind x12i:task", () => {
206
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
231
+ describe("node kinds", () => {
232
+ it("task nodes must use kind task", () => {
233
+ const doc = createMinimalExecutableGraph();
207
234
  doc.graph.nodes[0].kind = "task:wrong";
208
- const result = (0, api_js_1.validateExecutableGraph)(doc);
209
- strict_1.default.ok(result.errors.some((e) => e.code === "TASK_NODE_INVALID"));
235
+ const result = validateExecutableGraph(doc);
236
+ assert.ok(result.errors.some((e) => e.code === "TASK_NODE_INVALID"));
210
237
  });
211
238
  });
212
- (0, node_test_1.describe)("deterministic cases", () => {
213
- (0, node_test_1.it)("AC-001: runtime.mode eq simulate is accepted", () => {
214
- const errors = (0, api_js_1.validateCaseCondition)({
239
+ describe("deterministic cases", () => {
240
+ it("AC-001: runtime.mode eq simulate is accepted", () => {
241
+ const errors = validateCaseCondition({
215
242
  path: "runtime.mode",
216
243
  op: "eq",
217
244
  value: "simulate"
218
245
  });
219
- strict_1.default.equal(errors.length, 0);
246
+ assert.equal(errors.length, 0);
220
247
  });
221
- (0, node_test_1.it)("AC-007/008: first matching case is selected, else default", () => {
222
- const doc = setGraphModelConfig((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
248
+ it("AC-007/008: first matching case is selected, else default", () => {
249
+ const doc = setGraphModelConfig(createMinimalExecutableGraph(), {
223
250
  version: "graph-model-config/v1",
224
251
  cases: [
225
252
  {
@@ -241,12 +268,12 @@ function setGraphModelConfig(doc, modelConfig) {
241
268
  }
242
269
  ]
243
270
  });
244
- const context = (0, api_js_1.buildDeterministicCaseContext)(doc, { mode: "simulate" });
245
- const plan = (0, api_js_1.resolveNodeAiPlan)(doc, "node:professional-answer", context);
246
- strict_1.default.equal(plan.graphCaseId, "simulate");
271
+ const context = buildDeterministicCaseContext(doc, { mode: "simulate" });
272
+ const plan = resolveNodeAiPlan(doc, "node:professional-answer", context);
273
+ assert.equal(plan.graphCaseId, "simulate");
247
274
  });
248
- (0, node_test_1.it)("AC-009/010: default case requirements", () => {
249
- const noDefault = (0, api_js_1.validateExecutableGraph)(setGraphModelConfig((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
275
+ it("AC-009/010: default case requirements", () => {
276
+ const noDefault = validateExecutableGraph(setGraphModelConfig(createMinimalExecutableGraph(), {
250
277
  version: "graph-model-config/v1",
251
278
  cases: [
252
279
  {
@@ -260,51 +287,51 @@ function setGraphModelConfig(doc, modelConfig) {
260
287
  }
261
288
  ]
262
289
  }));
263
- strict_1.default.ok(noDefault.errors.some((e) => e.code === "CASE_SELECTION_DEFAULT_MISSING"));
290
+ assert.ok(noDefault.errors.some((e) => e.code === "CASE_SELECTION_DEFAULT_MISSING"));
264
291
  });
265
292
  });
266
- (0, node_test_1.describe)("forbidden AI selectors", () => {
267
- (0, node_test_1.it)("AC-020: ai.prompt is rejected", () => {
268
- const errors = (0, api_js_1.validateCaseCondition)({ ai: { prompt: "complex?" } });
269
- strict_1.default.ok(errors.some((e) => e.code === "CASE_CONDITION_FORBIDDEN_AI_SELECTOR"));
293
+ describe("forbidden AI selectors", () => {
294
+ it("AC-020: ai.prompt is rejected", () => {
295
+ const errors = validateCaseCondition({ ai: { prompt: "complex?" } });
296
+ assert.ok(errors.some((e) => e.code === "CASE_CONDITION_FORBIDDEN_AI_SELECTOR"));
270
297
  });
271
- (0, node_test_1.it)("AC-024: ai.classification path is rejected", () => {
272
- const errors = (0, api_js_1.validateCaseCondition)({
298
+ it("AC-024: ai.classification path is rejected", () => {
299
+ const errors = validateCaseCondition({
273
300
  path: "ai.classification.risk",
274
301
  op: "eq",
275
302
  value: "high"
276
303
  });
277
- strict_1.default.ok(errors.some((e) => e.code === "CASE_CONDITION_FORBIDDEN_PATH"));
304
+ assert.ok(errors.some((e) => e.code === "CASE_CONDITION_FORBIDDEN_PATH"));
278
305
  });
279
- (0, node_test_1.it)("AC-025: node.output path is rejected", () => {
280
- const errors = (0, api_js_1.validateCaseCondition)({
306
+ it("AC-025: node.output path is rejected", () => {
307
+ const errors = validateCaseCondition({
281
308
  path: "node.output.riskClassifier.risk",
282
309
  op: "eq",
283
310
  value: "high"
284
311
  });
285
- strict_1.default.ok(errors.some((e) => e.code === "CASE_CONDITION_FORBIDDEN_PATH"));
312
+ assert.ok(errors.some((e) => e.code === "CASE_CONDITION_FORBIDDEN_PATH"));
286
313
  });
287
314
  });
288
- (0, node_test_1.describe)("profile-choice validation", () => {
289
- (0, node_test_1.it)("AC-030/031/032: valid profileChoice keys accepted", () => {
290
- strict_1.default.equal((0, api_js_1.isProfileChoiceKeyFormat)("cheap/default"), true);
291
- strict_1.default.equal((0, api_js_1.isProfileChoiceKeyFormat)("vol/default"), true);
292
- strict_1.default.equal((0, api_js_1.isProfileChoiceKeyFormat)("deep/openai_deep"), true);
293
- strict_1.default.equal((0, api_js_1.isKnownProfileChoice)("vol/pro"), true);
294
- });
295
- (0, node_test_1.it)("AC-033/034/035/036: bare aliases rejected", () => {
315
+ describe("profile-choice validation", () => {
316
+ it("AC-030/031/032: valid profileChoice keys accepted", () => {
317
+ assert.equal(isProfileChoiceKeyFormat("cheap/default"), true);
318
+ assert.equal(isProfileChoiceKeyFormat("vol/default"), true);
319
+ assert.equal(isProfileChoiceKeyFormat("deep/openai_deep"), true);
320
+ assert.equal(isKnownProfileChoice("vol/pro"), true);
321
+ });
322
+ it("AC-033/034/035/036: bare aliases rejected", () => {
296
323
  for (const key of ["cheap", "balanced", "cheapest", "default"]) {
297
- strict_1.default.equal((0, api_js_1.isProfileChoiceKeyFormat)(key), false);
324
+ assert.equal(isProfileChoiceKeyFormat(key), false);
298
325
  }
299
326
  });
300
- (0, node_test_1.it)("AC-037/038: vendor slugs and legacy aliases rejected", () => {
327
+ it("AC-037/038: vendor slugs and legacy aliases rejected", () => {
301
328
  // Syntactically valid profile/choice shape, but not a bundled registry key.
302
- strict_1.default.equal((0, api_js_1.isProfileChoiceKeyFormat)("openai/gpt-4o-mini"), true);
303
- strict_1.default.equal((0, api_js_1.isKnownProfileChoice)("openai/gpt-4o-mini"), false);
304
- strict_1.default.equal((0, api_js_1.isProfileChoiceKeyFormat)("cheap@anthropic_cheap"), false);
329
+ assert.equal(isProfileChoiceKeyFormat("openai/gpt-4o-mini"), true);
330
+ assert.equal(isKnownProfileChoice("openai/gpt-4o-mini"), false);
331
+ assert.equal(isProfileChoiceKeyFormat("cheap@anthropic_cheap"), false);
305
332
  });
306
- (0, node_test_1.it)("AC-039: unknown choice rejected in graph validation", () => {
307
- const result = (0, api_js_1.validateExecutableGraph)(setGraphModelConfig((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
333
+ it("AC-039: unknown choice rejected in graph validation", () => {
334
+ const result = validateExecutableGraph(setGraphModelConfig(createMinimalExecutableGraph(), {
308
335
  version: "graph-model-config/v1",
309
336
  cases: [
310
337
  {
@@ -317,10 +344,10 @@ function setGraphModelConfig(doc, modelConfig) {
317
344
  }
318
345
  ]
319
346
  }));
320
- strict_1.default.ok(result.errors.some((e) => e.code === "PROFILE_CHOICE_KEY_UNKNOWN"));
347
+ assert.ok(result.errors.some((e) => e.code === "PROFILE_CHOICE_KEY_UNKNOWN"));
321
348
  });
322
- (0, node_test_1.it)("deprecated kind profile is rejected", () => {
323
- const result = (0, api_js_1.validateExecutableGraph)(setGraphModelConfig((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
349
+ it("deprecated kind profile is rejected", () => {
350
+ const result = validateExecutableGraph(setGraphModelConfig(createMinimalExecutableGraph(), {
324
351
  version: "graph-model-config/v1",
325
352
  cases: [
326
353
  {
@@ -333,13 +360,13 @@ function setGraphModelConfig(doc, modelConfig) {
333
360
  }
334
361
  ]
335
362
  }));
336
- strict_1.default.ok(result.errors.some((e) => e.code === "PROFILE_SELECTION_KIND_DEPRECATED"));
363
+ assert.ok(result.errors.some((e) => e.code === "PROFILE_SELECTION_KIND_DEPRECATED"));
337
364
  });
338
365
  });
339
- (0, node_test_1.describe)("normalization", () => {
340
- (0, node_test_1.it)("AC-060: graph default shorthand normalizes to cases[0].id = default", () => {
341
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
342
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
366
+ describe("normalization", () => {
367
+ it("AC-060: graph default shorthand normalizes to cases[0].id = default", () => {
368
+ const doc = createMinimalExecutableGraph();
369
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
343
370
  ext.modelConfig = {
344
371
  version: "graph-model-config/v1",
345
372
  default: {
@@ -348,25 +375,25 @@ function setGraphModelConfig(doc, modelConfig) {
348
375
  postActionModel: { kind: "profileChoice", key: "cheap/default" }
349
376
  }
350
377
  };
351
- const normalized = (0, api_js_1.normalizeExecutableGraph)(doc);
352
- const profile = normalized.graph.metadata?.extensions?.[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
353
- strict_1.default.equal(profile?.modelConfig?.cases?.[0]?.id, "default");
354
- strict_1.default.equal(profile?.modelConfig?.cases?.[0]?.when, undefined);
378
+ const normalized = normalizeExecutableGraph(doc);
379
+ const profile = normalized.graph.metadata?.extensions?.[EXECUTABLE_PROFILE_NAMESPACE];
380
+ assert.equal(profile?.modelConfig?.cases?.[0]?.id, "default");
381
+ assert.equal(profile?.modelConfig?.cases?.[0]?.when, undefined);
355
382
  });
356
- (0, node_test_1.it)("AC-066: normalization does not mutate source graph", () => {
357
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
383
+ it("AC-066: normalization does not mutate source graph", () => {
384
+ const doc = createMinimalExecutableGraph();
358
385
  const before = structuredClone(doc);
359
- (0, api_js_1.normalizeExecutableGraph)(doc);
360
- strict_1.default.deepEqual(doc, before);
386
+ normalizeExecutableGraph(doc);
387
+ assert.deepEqual(doc, before);
361
388
  });
362
389
  });
363
- (0, node_test_1.describe)("full resolution example", () => {
364
- (0, node_test_1.it)("matches CR/FR section 12 resolution", () => {
365
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
390
+ describe("full resolution example", () => {
391
+ it("matches CR/FR section 12 resolution", () => {
392
+ const doc = createMinimalExecutableGraph();
366
393
  const taskNode = doc.graph.nodes.find((n) => n.id === "node:professional-answer");
367
394
  const params = taskNode.parameters;
368
- strict_1.default.ok(params && params.nodeType === "task");
369
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
395
+ assert.ok(params && params.nodeType === "task");
396
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
370
397
  ext.modelConfig = {
371
398
  version: "graph-model-config/v1",
372
399
  cases: [
@@ -439,51 +466,51 @@ function setGraphModelConfig(doc, modelConfig) {
439
466
  }
440
467
  }
441
468
  };
442
- const context = (0, api_js_1.buildDeterministicCaseContext)(doc, {
469
+ const context = buildDeterministicCaseContext(doc, {
443
470
  mode: "live",
444
471
  input: { analysisDepth: "deep", riskLevel: "high" }
445
472
  });
446
- const plan = (0, api_js_1.resolveNodeAiPlan)(doc, "node:professional-answer", context);
447
- strict_1.default.equal(plan.graphCaseId, "deep-live");
448
- strict_1.default.equal(plan.nodeCaseId, "high-risk-input");
449
- strict_1.default.equal(plan.slots.preActionModel.selected.kind, "profileChoice");
473
+ const plan = resolveNodeAiPlan(doc, "node:professional-answer", context);
474
+ assert.equal(plan.graphCaseId, "deep-live");
475
+ assert.equal(plan.nodeCaseId, "high-risk-input");
476
+ assert.equal(plan.slots.preActionModel.selected.kind, "profileChoice");
450
477
  if (plan.slots.preActionModel.selected.kind === "profileChoice") {
451
- strict_1.default.equal(plan.slots.preActionModel.selected.key, "vol/default");
478
+ assert.equal(plan.slots.preActionModel.selected.key, "vol/default");
452
479
  }
453
480
  if (plan.slots.skillModel.selected.kind === "profileChoice") {
454
- strict_1.default.equal(plan.slots.skillModel.selected.key, "deep/openai_deep");
481
+ assert.equal(plan.slots.skillModel.selected.key, "deep/openai_deep");
455
482
  }
456
- strict_1.default.ok(plan.caseSelection.graph.matchedConditions.some((c) => c.includes("runtime.mode eq live")));
457
- strict_1.default.ok(plan.caseSelection.node?.matchedConditions.some((c) => c.includes("runtime.input.riskLevel eq high")));
483
+ assert.ok(plan.caseSelection.graph.matchedConditions.some((c) => c.includes("runtime.mode eq live")));
484
+ assert.ok(plan.caseSelection.node?.matchedConditions.some((c) => c.includes("runtime.input.riskLevel eq high")));
458
485
  });
459
486
  });
460
- (0, node_test_1.describe)("evaluateCaseCondition", () => {
461
- (0, node_test_1.it)("AC-004/005/006: all, any, not supported", () => {
462
- const context = (0, api_js_1.buildDeterministicCaseContext)((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
487
+ describe("evaluateCaseCondition", () => {
488
+ it("AC-004/005/006: all, any, not supported", () => {
489
+ const context = buildDeterministicCaseContext(createMinimalExecutableGraph(), {
463
490
  mode: "live",
464
491
  input: { riskLevel: "high", tier: "gold" }
465
492
  });
466
- strict_1.default.equal((0, api_js_1.evaluateCaseCondition)({
493
+ assert.equal(evaluateCaseCondition({
467
494
  all: [
468
495
  { path: "runtime.mode", op: "eq", value: "live" },
469
496
  { path: "runtime.input.riskLevel", op: "eq", value: "high" }
470
497
  ]
471
498
  }, context), true);
472
- strict_1.default.equal((0, api_js_1.evaluateCaseCondition)({
499
+ assert.equal(evaluateCaseCondition({
473
500
  any: [
474
501
  { path: "runtime.input.tier", op: "eq", value: "silver" },
475
502
  { path: "runtime.input.tier", op: "eq", value: "gold" }
476
503
  ]
477
504
  }, context), true);
478
- strict_1.default.equal((0, api_js_1.evaluateCaseCondition)({
505
+ assert.equal(evaluateCaseCondition({
479
506
  not: { path: "runtime.mode", op: "eq", value: "simulate" }
480
507
  }, context), true);
481
508
  });
482
509
  });
483
- (0, node_test_1.describe)("lifecycle artifacts", () => {
484
- (0, node_test_1.it)("AC-A001/A005: authoring graph with modelConfig.default passes", () => {
485
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
486
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
510
+ describe("lifecycle artifacts", () => {
511
+ it("AC-A001/A005: authoring graph with modelConfig.default passes", () => {
512
+ const doc = createMinimalExecutableGraph();
513
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
487
514
  ext.modelConfig = {
488
515
  version: "graph-model-config/v1",
489
516
  default: {
@@ -492,10 +519,10 @@ function setGraphModelConfig(doc, modelConfig) {
492
519
  postActionModel: { kind: "profileChoice", key: "cheap/default" }
493
520
  }
494
521
  };
495
- strict_1.default.equal((0, api_js_1.validateAuthoringGraph)(doc).valid, true);
522
+ assert.equal(validateAuthoringGraph(doc).valid, true);
496
523
  });
497
- (0, node_test_1.it)("AC-A003/A004: bare profile and kind profile fail authoring validation", () => {
498
- const bareProfile = (0, api_js_1.validateAuthoringGraph)(setGraphModelConfig((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
524
+ it("AC-A003/A004: bare profile and kind profile fail authoring validation", () => {
525
+ const bareProfile = validateAuthoringGraph(setGraphModelConfig(createMinimalExecutableGraph(), {
499
526
  version: "graph-model-config/v1",
500
527
  cases: [
501
528
  {
@@ -508,8 +535,8 @@ function setGraphModelConfig(doc, modelConfig) {
508
535
  }
509
536
  ]
510
537
  }));
511
- strict_1.default.ok(bareProfile.errors.some((e) => e.code === "PROFILE_CHOICE_KEY_FORMAT_INVALID"));
512
- const kindProfile = (0, api_js_1.validateAuthoringGraph)(setGraphModelConfig((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
538
+ assert.ok(bareProfile.errors.some((e) => e.code === "PROFILE_CHOICE_KEY_FORMAT_INVALID"));
539
+ const kindProfile = validateAuthoringGraph(setGraphModelConfig(createMinimalExecutableGraph(), {
513
540
  version: "graph-model-config/v1",
514
541
  cases: [
515
542
  {
@@ -522,11 +549,11 @@ function setGraphModelConfig(doc, modelConfig) {
522
549
  }
523
550
  ]
524
551
  }));
525
- strict_1.default.ok(kindProfile.errors.some((e) => e.code === "PROFILE_SELECTION_KIND_DEPRECATED"));
552
+ assert.ok(kindProfile.errors.some((e) => e.code === "PROFILE_SELECTION_KIND_DEPRECATED"));
526
553
  });
527
- (0, node_test_1.it)("AC-P001/P003/P008/P009/P010: compile produces run-bound executable plan", () => {
528
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
529
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
554
+ it("AC-P001/P003/P008/P009/P010: compile produces run-bound executable plan", () => {
555
+ const doc = createMinimalExecutableGraph();
556
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
530
557
  ext.modelConfig = {
531
558
  version: "graph-model-config/v1",
532
559
  cases: [
@@ -549,57 +576,57 @@ function setGraphModelConfig(doc, modelConfig) {
549
576
  }
550
577
  ]
551
578
  };
552
- const runtime = (0, api_js_1.buildRuntimeObject)({
579
+ const runtime = buildRuntimeObject({
553
580
  jobId: "job-compile-1",
554
581
  mode: "simulate",
555
582
  input: { target_subnet_cidr: "10.0.0.0/24" }
556
583
  });
557
584
  const before = structuredClone(doc);
558
- const plan = (0, api_js_1.compileExecutablePlan)(doc, runtime, {
585
+ const plan = compileExecutablePlan(doc, runtime, {
559
586
  profileRegistry: { version: "3.0.0", registryHash: "sha256:profiles456" },
560
587
  environment: "prod"
561
588
  });
562
- strict_1.default.deepEqual(doc, before);
563
- strict_1.default.equal(plan.format, "x12i.graphenix.executable-plan/v1");
564
- strict_1.default.equal(plan.source.graphId, doc.id);
565
- strict_1.default.equal(plan.runtimeBinding.jobId, "job-compile-1");
566
- strict_1.default.equal(plan.caseSelection.graph.caseId, "simulate");
567
- strict_1.default.equal(plan.profileRegistry.version, "3.0.0");
568
- const profileExt = plan.graph.graph.metadata?.extensions?.[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
569
- strict_1.default.equal("default" in (profileExt?.modelConfig ?? {}), false);
589
+ assert.deepEqual(doc, before);
590
+ assert.equal(plan.format, "graphenix.executable-plan/v1");
591
+ assert.equal(plan.source.graphId, doc.id);
592
+ assert.equal(plan.runtimeBinding.jobId, "job-compile-1");
593
+ assert.equal(plan.caseSelection.graph.caseId, "simulate");
594
+ assert.equal(plan.profileRegistry.version, "3.0.0");
595
+ const profileExt = plan.graph.graph.metadata?.extensions?.[EXECUTABLE_PROFILE_NAMESPACE];
596
+ assert.equal("default" in (profileExt?.modelConfig ?? {}), false);
570
597
  const professionalPlan = plan.nodePlans["node:professional-answer"];
571
- strict_1.default.equal(professionalPlan?.modelSlots?.skillModel?.selection.kind, "profileChoice");
572
- strict_1.default.equal((0, api_js_1.validateExecutablePlan)(plan).valid, true);
573
- });
574
- (0, node_test_1.it)("AC-E003/E006/E008: executable plan is normalized with resolved node slots", () => {
575
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
576
- const runtime = (0, api_js_1.buildRuntimeObject)({ jobId: "job-plan-1" });
577
- const plan = (0, api_js_1.compileExecutablePlan)(doc, runtime);
578
- strict_1.default.equal((0, api_js_1.validateExecutablePlan)(plan).valid, true);
579
- strict_1.default.ok(plan.nodePlans["node:professional-answer"]?.modelSlots?.preActionModel);
580
- strict_1.default.equal("credentials" in plan, false);
581
- });
582
- (0, node_test_1.it)("AC-T001/T002/T011: execution trace references plan and keeps append-only events", () => {
583
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
584
- const runtime = (0, api_js_1.buildRuntimeObject)({ jobId: "job-trace-1", mode: "live" });
585
- const plan = (0, api_js_1.compileExecutablePlan)(doc, runtime);
586
- const trace = (0, api_js_1.createExecutionTrace)(plan, runtime);
587
- strict_1.default.equal(trace.source.graphId, plan.source.graphId);
588
- strict_1.default.equal(trace.plan.planId, plan.planId);
589
- strict_1.default.equal(trace.status, "queued");
598
+ assert.equal(professionalPlan?.modelSlots?.skillModel?.selection.kind, "profileChoice");
599
+ assert.equal(validateExecutablePlan(plan).valid, true);
600
+ });
601
+ it("AC-E003/E006/E008: executable plan is normalized with resolved node slots", () => {
602
+ const doc = createMinimalExecutableGraph();
603
+ const runtime = buildRuntimeObject({ jobId: "job-plan-1" });
604
+ const plan = compileExecutablePlan(doc, runtime);
605
+ assert.equal(validateExecutablePlan(plan).valid, true);
606
+ assert.ok(plan.nodePlans["node:professional-answer"]?.modelSlots?.preActionModel);
607
+ assert.equal("credentials" in plan, false);
608
+ });
609
+ it("AC-T001/T002/T011: execution trace references plan and keeps append-only events", () => {
610
+ const doc = createMinimalExecutableGraph();
611
+ const runtime = buildRuntimeObject({ jobId: "job-trace-1", mode: "live" });
612
+ const plan = compileExecutablePlan(doc, runtime);
613
+ const trace = createExecutionTrace(plan, runtime);
614
+ assert.equal(trace.source.graphId, plan.source.graphId);
615
+ assert.equal(trace.plan.planId, plan.planId);
616
+ assert.equal(trace.status, "queued");
590
617
  const startedAt = "2026-06-06T12:00:01.000Z";
591
- const updated = (0, api_js_1.appendExecutionEvent)(trace, {
618
+ const updated = appendExecutionEvent(trace, {
592
619
  id: "evt:1",
593
620
  ts: startedAt,
594
621
  level: "info",
595
622
  type: "graph.started",
596
623
  message: "Graph execution started."
597
624
  });
598
- strict_1.default.equal(updated.events.length, 1);
599
- strict_1.default.notEqual(updated, trace);
600
- strict_1.default.equal((0, api_js_1.validateExecutionTrace)(updated, plan.nodePlans).valid, true);
625
+ assert.equal(updated.events.length, 1);
626
+ assert.notEqual(updated, trace);
627
+ assert.equal(validateExecutionTrace(updated, plan.nodePlans).valid, true);
601
628
  const nodeTrace = updated.nodeExecutions["node:professional-answer"];
602
- strict_1.default.ok(nodeTrace?.units["unit:node:professional-answer:skill"]);
629
+ assert.ok(nodeTrace?.units["unit:node:professional-answer:skill"]);
603
630
  });
604
631
  });
605
632
  function getTaskNode(doc, nodeId = "node:professional-answer") {
@@ -608,7 +635,7 @@ function getTaskNode(doc, nodeId = "node:professional-answer") {
608
635
  function setTaskConfiguration(doc, config) {
609
636
  const node = getTaskNode(doc);
610
637
  const params = node.parameters;
611
- strict_1.default.ok(params && params.nodeType === "task");
638
+ assert.ok(params && params.nodeType === "task");
612
639
  node.parameters = {
613
640
  ...params,
614
641
  taskConfiguration: config
@@ -616,22 +643,22 @@ function setTaskConfiguration(doc, config) {
616
643
  return doc;
617
644
  }
618
645
  function setGraphPolicies(doc, policies) {
619
- const ext = doc.graph.metadata.extensions[constants_js_1.EXECUTABLE_PROFILE_NAMESPACE];
646
+ const ext = doc.graph.metadata.extensions[EXECUTABLE_PROFILE_NAMESPACE];
620
647
  ext.policies = policies;
621
648
  return doc;
622
649
  }
623
- (0, node_test_1.describe)("execution units", () => {
624
- (0, node_test_1.it)("AC-001: task node with no preActions/postActions compiles into one skill unit", () => {
625
- const doc = (0, minimal_executable_graph_js_1.createMinimalExecutableGraph)();
626
- const runtime = (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-1" });
627
- const plan = (0, api_js_1.compileExecutablePlan)(doc, runtime);
650
+ describe("execution units", () => {
651
+ it("AC-001: task node with no preActions/postActions compiles into one skill unit", () => {
652
+ const doc = createMinimalExecutableGraph();
653
+ const runtime = buildRuntimeObject({ jobId: "job-units-1" });
654
+ const plan = compileExecutablePlan(doc, runtime);
628
655
  const units = plan.nodePlans["node:professional-answer"].executionUnits;
629
- strict_1.default.equal(units.length, 1);
630
- strict_1.default.equal(units[0].unitKind, "skill");
631
- strict_1.default.equal(units[0].unitId, "unit:node:professional-answer:skill");
656
+ assert.equal(units.length, 1);
657
+ assert.equal(units[0].unitKind, "skill");
658
+ assert.equal(units[0].unitId, "unit:node:professional-answer:skill");
632
659
  });
633
- (0, node_test_1.it)("AC-002/003/004: preActions before skill and postActions after with stable order", () => {
634
- const doc = setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
660
+ it("AC-002/003/004: preActions before skill and postActions after with stable order", () => {
661
+ const doc = setTaskConfiguration(createMinimalExecutableGraph(), {
635
662
  preActions: [
636
663
  { id: "pre:a", actionKey: "prepare-input" },
637
664
  { id: "pre:b", actionKey: "normalize-input" }
@@ -641,10 +668,10 @@ function setGraphPolicies(doc, policies) {
641
668
  { id: "post:b", actionKey: "shape-response" }
642
669
  ]
643
670
  });
644
- const plan = (0, api_js_1.compileExecutablePlan)(doc, (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-2" }));
671
+ const plan = compileExecutablePlan(doc, buildRuntimeObject({ jobId: "job-units-2" }));
645
672
  const units = plan.nodePlans["node:professional-answer"].executionUnits;
646
- strict_1.default.equal(units.length, 5);
647
- strict_1.default.deepEqual(units.map((unit) => [unit.order, unit.unitKind, unit.actionKey ?? unit.skillKey]), [
673
+ assert.equal(units.length, 5);
674
+ assert.deepEqual(units.map((unit) => [unit.order, unit.unitKind, unit.actionKey ?? unit.skillKey]), [
648
675
  [0, "preAction", "prepare-input"],
649
676
  [1, "preAction", "normalize-input"],
650
677
  [2, "skill", "professional-answer"],
@@ -652,31 +679,31 @@ function setGraphPolicies(doc, policies) {
652
679
  [4, "postAction", "shape-response"]
653
680
  ]);
654
681
  });
655
- (0, node_test_1.it)("AC-005/006/007: units use resolved node model slots", () => {
656
- const doc = setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
682
+ it("AC-005/006/007: units use resolved node model slots", () => {
683
+ const doc = setTaskConfiguration(createMinimalExecutableGraph(), {
657
684
  preActions: [{ id: "pre:a", actionKey: "prepare-input" }],
658
685
  postActions: [{ id: "post:a", actionKey: "validate-output" }]
659
686
  });
660
- const plan = (0, api_js_1.compileExecutablePlan)(doc, (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-3" }));
687
+ const plan = compileExecutablePlan(doc, buildRuntimeObject({ jobId: "job-units-3" }));
661
688
  const nodePlan = plan.nodePlans["node:professional-answer"];
662
689
  const pre = nodePlan.executionUnits.find((unit) => unit.unitKind === "preAction");
663
690
  const skill = nodePlan.executionUnits.find((unit) => unit.unitKind === "skill");
664
691
  const post = nodePlan.executionUnits.find((unit) => unit.unitKind === "postAction");
665
- strict_1.default.equal(pre.modelSlot, "preActionModel");
692
+ assert.equal(pre.modelSlot, "preActionModel");
666
693
  if (pre.modelSelection?.kind === "profileChoice") {
667
- strict_1.default.equal(pre.modelSelection.key, "cheap/default");
694
+ assert.equal(pre.modelSelection.key, "cheap/default");
668
695
  }
669
- strict_1.default.equal(skill.modelSlot, "skillModel");
696
+ assert.equal(skill.modelSlot, "skillModel");
670
697
  if (skill.modelSelection?.kind === "profileChoice") {
671
- strict_1.default.equal(skill.modelSelection.key, "vol/default");
698
+ assert.equal(skill.modelSelection.key, "vol/default");
672
699
  }
673
- strict_1.default.equal(post.modelSlot, "postActionModel");
700
+ assert.equal(post.modelSlot, "postActionModel");
674
701
  if (post.modelSelection?.kind === "profileChoice") {
675
- strict_1.default.equal(post.modelSelection.key, "cheap/default");
702
+ assert.equal(post.modelSelection.key, "cheap/default");
676
703
  }
677
704
  });
678
- (0, node_test_1.it)("AC-008/009: node skillModel override does not affect pre/post units", () => {
679
- const doc = setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
705
+ it("AC-008/009: node skillModel override does not affect pre/post units", () => {
706
+ const doc = setTaskConfiguration(createMinimalExecutableGraph(), {
680
707
  modelConfig: {
681
708
  inherit: true,
682
709
  modelConfig: {
@@ -686,23 +713,23 @@ function setGraphPolicies(doc, policies) {
686
713
  preActions: [{ id: "pre:a", actionKey: "prepare-input" }],
687
714
  postActions: [{ id: "post:a", actionKey: "validate-output" }]
688
715
  });
689
- const plan = (0, api_js_1.compileExecutablePlan)(doc, (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-4" }));
716
+ const plan = compileExecutablePlan(doc, buildRuntimeObject({ jobId: "job-units-4" }));
690
717
  const units = plan.nodePlans["node:professional-answer"].executionUnits;
691
718
  const pre = units.find((unit) => unit.unitKind === "preAction");
692
719
  const skill = units.find((unit) => unit.unitKind === "skill");
693
720
  const post = units.find((unit) => unit.unitKind === "postAction");
694
721
  if (pre.modelSelection?.kind === "profileChoice") {
695
- strict_1.default.equal(pre.modelSelection.key, "cheap/default");
722
+ assert.equal(pre.modelSelection.key, "cheap/default");
696
723
  }
697
724
  if (skill.modelSelection?.kind === "profileChoice") {
698
- strict_1.default.equal(skill.modelSelection.key, "deep/openai_deep");
725
+ assert.equal(skill.modelSelection.key, "deep/openai_deep");
699
726
  }
700
727
  if (post.modelSelection?.kind === "profileChoice") {
701
- strict_1.default.equal(post.modelSelection.key, "cheap/default");
728
+ assert.equal(post.modelSelection.key, "cheap/default");
702
729
  }
703
730
  });
704
- (0, node_test_1.it)("AC-010: action-level model override fails when policy disabled", () => {
705
- const doc = setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
731
+ it("AC-010: action-level model override fails when policy disabled", () => {
732
+ const doc = setTaskConfiguration(createMinimalExecutableGraph(), {
706
733
  preActions: [
707
734
  {
708
735
  id: "pre:a",
@@ -711,11 +738,11 @@ function setGraphPolicies(doc, policies) {
711
738
  }
712
739
  ]
713
740
  });
714
- const result = (0, api_js_1.validateAuthoringGraph)(doc);
715
- strict_1.default.ok(result.errors.some((e) => e.code === "TASK_ACTION_MODEL_OVERRIDE_FORBIDDEN"));
741
+ const result = validateAuthoringGraph(doc);
742
+ assert.ok(result.errors.some((e) => e.code === "TASK_ACTION_MODEL_OVERRIDE_FORBIDDEN"));
716
743
  });
717
- (0, node_test_1.it)("AC-011/012: action-level model override passes when policy enabled", () => {
718
- const doc = setGraphPolicies(setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
744
+ it("AC-011/012: action-level model override passes when policy enabled", () => {
745
+ const doc = setGraphPolicies(setTaskConfiguration(createMinimalExecutableGraph(), {
719
746
  preActions: [
720
747
  {
721
748
  id: "pre:a",
@@ -724,16 +751,16 @@ function setGraphPolicies(doc, policies) {
724
751
  }
725
752
  ]
726
753
  }), { allowActionLevelModelOverride: true });
727
- strict_1.default.equal((0, api_js_1.validateAuthoringGraph)(doc).valid, true);
728
- const plan = (0, api_js_1.compileExecutablePlan)(doc, (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-5" }));
754
+ assert.equal(validateAuthoringGraph(doc).valid, true);
755
+ const plan = compileExecutablePlan(doc, buildRuntimeObject({ jobId: "job-units-5" }));
729
756
  const pre = plan.nodePlans["node:professional-answer"].executionUnits[0];
730
- strict_1.default.equal(pre.modelSource, "actionOverride");
757
+ assert.equal(pre.modelSource, "actionOverride");
731
758
  if (pre.modelSelection?.kind === "profileChoice") {
732
- strict_1.default.equal(pre.modelSelection.key, "vol/pro");
759
+ assert.equal(pre.modelSelection.key, "vol/pro");
733
760
  }
734
761
  });
735
- (0, node_test_1.it)("AC-013: bare profile key in action-level override fails", () => {
736
- const doc = setGraphPolicies(setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
762
+ it("AC-013: bare profile key in action-level override fails", () => {
763
+ const doc = setGraphPolicies(setTaskConfiguration(createMinimalExecutableGraph(), {
737
764
  preActions: [
738
765
  {
739
766
  id: "pre:a",
@@ -742,11 +769,11 @@ function setGraphPolicies(doc, policies) {
742
769
  }
743
770
  ]
744
771
  }), { allowActionLevelModelOverride: true });
745
- const result = (0, api_js_1.validateAuthoringGraph)(doc);
746
- strict_1.default.ok(result.errors.some((e) => e.code === "PROFILE_CHOICE_KEY_FORMAT_INVALID"));
772
+ const result = validateAuthoringGraph(doc);
773
+ assert.ok(result.errors.some((e) => e.code === "PROFILE_CHOICE_KEY_FORMAT_INVALID"));
747
774
  });
748
- (0, node_test_1.it)("AC-014/015/016: unit fallback stays on same slot only", () => {
749
- const resolvedPre = (0, api_js_1.resolveNodeModelSlot)({
775
+ it("AC-014/015/016: unit fallback stays on same slot only", () => {
776
+ const resolvedPre = resolveNodeModelSlot({
750
777
  slot: "preActionModel",
751
778
  graphSelection: { kind: "profileChoice", key: "cheap/default" },
752
779
  nodeSelection: { kind: "profileChoice", key: "vol/pro" },
@@ -762,29 +789,29 @@ function setGraphPolicies(doc, policies) {
762
789
  graphCaseId: "default",
763
790
  nodeId: "node:professional-answer"
764
791
  });
765
- strict_1.default.equal(resolvedPre.source, "fallbackToGraphDefault");
792
+ assert.equal(resolvedPre.source, "fallbackToGraphDefault");
766
793
  if (resolvedPre.selected.kind === "profileChoice") {
767
- strict_1.default.equal(resolvedPre.selected.key, "cheap/default");
794
+ assert.equal(resolvedPre.selected.key, "cheap/default");
768
795
  }
769
- const plan = (0, api_js_1.compileExecutablePlan)(setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
796
+ const plan = compileExecutablePlan(setTaskConfiguration(createMinimalExecutableGraph(), {
770
797
  preActions: [{ id: "pre:a", actionKey: "prepare-input" }],
771
798
  postActions: [{ id: "post:a", actionKey: "validate-output" }]
772
- }), (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-fallback" }));
799
+ }), buildRuntimeObject({ jobId: "job-units-fallback" }));
773
800
  const units = plan.nodePlans["node:professional-answer"].executionUnits;
774
- strict_1.default.ok(units.every((unit) => unit.modelSlot !== "skillModel" || unit.unitKind === "skill"));
775
- strict_1.default.ok(units.every((unit) => unit.modelSlot !== "postActionModel" || unit.unitKind === "postAction"));
776
- strict_1.default.ok(units.every((unit) => unit.modelSlot !== "preActionModel" || unit.unitKind === "preAction"));
801
+ assert.ok(units.every((unit) => unit.modelSlot !== "skillModel" || unit.unitKind === "skill"));
802
+ assert.ok(units.every((unit) => unit.modelSlot !== "postActionModel" || unit.unitKind === "postAction"));
803
+ assert.ok(units.every((unit) => unit.modelSlot !== "preActionModel" || unit.unitKind === "preAction"));
777
804
  });
778
- (0, node_test_1.it)("AC-017/018/019: execution trace records planned units and unit fallback", () => {
779
- const doc = setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
805
+ it("AC-017/018/019: execution trace records planned units and unit fallback", () => {
806
+ const doc = setTaskConfiguration(createMinimalExecutableGraph(), {
780
807
  preActions: [{ id: "pre:a", actionKey: "prepare-input" }],
781
808
  postActions: [{ id: "post:a", actionKey: "validate-output" }]
782
809
  });
783
- const runtime = (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-6" });
784
- const plan = (0, api_js_1.compileExecutablePlan)(doc, runtime);
785
- const trace = (0, api_js_1.createExecutionTrace)(plan, runtime);
810
+ const runtime = buildRuntimeObject({ jobId: "job-units-6" });
811
+ const plan = compileExecutablePlan(doc, runtime);
812
+ const trace = createExecutionTrace(plan, runtime);
786
813
  const nodeTrace = trace.nodeExecutions["node:professional-answer"];
787
- strict_1.default.equal(Object.keys(nodeTrace.units).length, 3);
814
+ assert.equal(Object.keys(nodeTrace.units).length, 3);
788
815
  const skillUnitId = "unit:node:professional-answer:skill";
789
816
  nodeTrace.units[skillUnitId] = {
790
817
  ...nodeTrace.units[skillUnitId],
@@ -811,8 +838,8 @@ function setGraphPolicies(doc, policies) {
811
838
  enabled: true,
812
839
  allowedTriggers: ["nodeModelUnavailable"]
813
840
  };
814
- strict_1.default.equal((0, api_js_1.validateExecutionTrace)(invalidFallback, invalidPolicyPlan.nodePlans).valid, false);
815
- const withEvent = (0, api_js_1.appendExecutionEvent)(trace, {
841
+ assert.equal(validateExecutionTrace(invalidFallback, invalidPolicyPlan.nodePlans).valid, false);
842
+ const withEvent = appendExecutionEvent(trace, {
816
843
  id: "evt:unit:1",
817
844
  ts: "2026-06-06T12:00:02.100Z",
818
845
  level: "info",
@@ -826,18 +853,18 @@ function setGraphPolicies(doc, policies) {
826
853
  source: "graphDefault"
827
854
  }
828
855
  });
829
- strict_1.default.equal(withEvent.events[0].type, "executionUnit.model.resolved");
856
+ assert.equal(withEvent.events[0].type, "executionUnit.model.resolved");
830
857
  });
831
- (0, node_test_1.it)("AC-020: graph, plan, and trace remain implementation-agnostic", () => {
832
- const doc = setTaskConfiguration((0, minimal_executable_graph_js_1.createMinimalExecutableGraph)(), {
858
+ it("AC-020: graph, plan, and trace remain implementation-agnostic", () => {
859
+ const doc = setTaskConfiguration(createMinimalExecutableGraph(), {
833
860
  preActions: [{ id: "pre:a", actionKey: "prepare-input" }]
834
861
  });
835
- const runtime = (0, api_js_1.buildRuntimeObject)({ jobId: "job-units-7" });
836
- const plan = (0, api_js_1.compileExecutablePlan)(doc, runtime);
837
- const trace = (0, api_js_1.createExecutionTrace)(plan, runtime);
862
+ const runtime = buildRuntimeObject({ jobId: "job-units-7" });
863
+ const plan = compileExecutablePlan(doc, runtime);
864
+ const trace = createExecutionTrace(plan, runtime);
838
865
  const serialized = JSON.stringify({ doc, plan, trace });
839
866
  for (const forbidden of ["openrouter", "anthropic-sdk", "langchain"]) {
840
- strict_1.default.equal(serialized.includes(forbidden), false);
867
+ assert.equal(serialized.includes(forbidden), false);
841
868
  }
842
869
  });
843
870
  });