@exellix/graph-engine 8.0.0 → 8.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +27 -1
- package/README.md +11 -12
- package/dist/src/compile/authoringDocumentHelpers.d.ts +9 -0
- package/dist/src/compile/authoringDocumentHelpers.js +18 -0
- package/dist/src/compile/compileExellixExecutablePlan.d.ts +8 -0
- package/dist/src/compile/compileExellixExecutablePlan.js +75 -0
- package/dist/src/index.d.ts +4 -6
- package/dist/src/index.js +2 -4
- package/dist/src/runtime/ExellixGraphRuntime.d.ts +11 -37
- package/dist/src/runtime/ExellixGraphRuntime.js +78 -173
- package/dist/src/runtime/aiTasksStrategyPhases.js +7 -3
- package/dist/src/runtime/buildAiTasksRunTaskRequest.d.ts +6 -8
- package/dist/src/runtime/buildAiTasksRunTaskRequest.js +2 -7
- package/dist/src/runtime/executionMatrixHost.d.ts +6 -3
- package/dist/src/runtime/executionMatrixHost.js +6 -4
- package/dist/src/runtime/runTaskNodePlan.d.ts +15 -0
- package/dist/src/runtime/runTaskNodePlan.js +46 -0
- package/dist/src/runtime/studioGraphExecuteRequest.d.ts +5 -30
- package/dist/src/runtime/studioGraphExecuteRequest.js +14 -50
- package/dist/src/runtime/taskNodeRunTaskPreflight.d.ts +7 -5
- package/dist/src/runtime/taskNodeRunTaskPreflight.js +31 -26
- package/dist/src/types/refs.d.ts +1 -1
- package/dist/testkit/authoringGraphFixtures.d.ts +8 -0
- package/dist/testkit/authoringGraphFixtures.js +249 -0
- package/dist/testkit/buildExecuteGraphInput.d.ts +3 -3
- package/dist/testkit/buildExecuteGraphInput.js +8 -4
- package/dist/testkit/flatGraphToAuthoring.d.ts +29 -0
- package/dist/testkit/flatGraphToAuthoring.js +281 -0
- package/dist/testkit/index.d.ts +3 -0
- package/dist/testkit/index.js +3 -0
- package/dist/testkit/runTaskNodePlanAssertions.d.ts +34 -0
- package/dist/testkit/runTaskNodePlanAssertions.js +32 -0
- package/package.json +8 -7
- package/dist/src/adapters/compileExellixExecutablePlan.d.ts +0 -8
- package/dist/src/adapters/compileExellixExecutablePlan.js +0 -18
- package/dist/src/adapters/migrateExellixGraphModelToAuthoring.d.ts +0 -6
- package/dist/src/adapters/migrateExellixGraphModelToAuthoring.js +0 -273
- package/dist/src/adapters/patchFinalizerPlans.d.ts +0 -7
- package/dist/src/adapters/patchFinalizerPlans.js +0 -63
- package/dist/src/runtime/graphResponseMigration.d.ts +0 -7
- package/dist/src/runtime/graphResponseMigration.js +0 -44
|
@@ -2,16 +2,12 @@ import { createExecutionTrace, appendExecutionEvent, validateExecutionTrace } fr
|
|
|
2
2
|
import { preparePlanExecuteEntry, computePlanAudit } from "../plan/planExecuteEntry.js";
|
|
3
3
|
import { embeddedGraphToExellixGraph } from "../plan/embeddedGraphToExellixGraph.js";
|
|
4
4
|
import { graphAiModelConfigFromFinalizerPlan, graphAiModelConfigFromNodePlan } from "../plan/planModelConfig.js";
|
|
5
|
-
import { executionPipelineFromNodePlan } from "../plan/planExecutionPipeline.js";
|
|
6
5
|
import { applyNodePlanInvoke, finalizerPlanForId, nodePlanForId } from "../plan/applyNodePlanInvoke.js";
|
|
7
6
|
import { evaluateDeferredNodeGate, evaluateDeferredEdgeGate, nodeDeferredGate, hasPlanConditionalEdges, evaluatePlanEntryGates, planNeedsRunx, } from "../plan/planDeferredGates.js";
|
|
8
7
|
import { mergeExecutionObject, copyExecutionContextFields, } from "./memory.js";
|
|
9
8
|
import { buildAiTasksRunTaskRequest, extractRunTaskStrategyOverrides, resolveJobTypeId, } from "./buildAiTasksRunTaskRequest.js";
|
|
10
9
|
import { runTaskResponseSucceeded } from "./runTaskResponse.js";
|
|
11
|
-
import { getAiTaskProfileStrategyKeys, runEngineAiTasksStrategyPhase, } from "./aiTasksStrategyPhases.js";
|
|
12
10
|
import { mergeGraphDocumentModel, EXELLIX_GRAPH_MODEL_VARIABLE_KEY, } from "../types/refs.js";
|
|
13
|
-
import { normalizeSynthesizedContextConfig } from "./synthesizedContextPipeline.js";
|
|
14
|
-
import { resolveExecutionPipelineForTaskNode } from "./resolveExecutionPipelineForTaskNode.js";
|
|
15
11
|
import { resolveTaskNodeInputsForRunTask } from "./resolveTaskNodeInputs.js";
|
|
16
12
|
import { assertAiTasksNodeExtensionsValid } from "../inspection/validateAiTasksNodeExtensions.js";
|
|
17
13
|
import { buildRunTaskMainInput, extractCallerInputsBag } from "./resolveGraphEngineMemoryPaths.js";
|
|
@@ -25,13 +21,13 @@ import { executeDeterministicFinalizer, executeSynthesizeFinalizer } from "./fin
|
|
|
25
21
|
import { createFinalizerError } from "./finalizers/errors.js";
|
|
26
22
|
import { assertCanonicalGraphRuntimeObject } from "./validateCanonicalGraphRuntime.js";
|
|
27
23
|
import { applyGraphResponseDefinition } from "./graphResponseMapping.js";
|
|
28
|
-
import { migrateLegacyGraphResponse } from "./graphResponseMigration.js";
|
|
29
24
|
import { buildAiTasksObservabilityRecord } from "./aiTasksObservability.js";
|
|
30
|
-
import {
|
|
25
|
+
import { buildRunTaskIdentityEnvelope, shouldForwardRunTaskTraceMode, } from "./runTaskAugments.js";
|
|
31
26
|
import { buildRunLog, extractLogxerCorrelationFromMetadata, extractTaskRunLogFromMetadata, resolveRunLogLimits, } from "./buildRunLog.js";
|
|
32
27
|
import { setRuntimeObjectsLastJobId, summarizeRuntimeObjectsForPlayground } from "./runtimeObjects.js";
|
|
33
28
|
import { DebugLogAbstract, bindGraphEngineRunLogxer, clearGraphEngineRunLogxer, createGraphEngineLogxer, ensureGraphEngineLogxerOnRuntimeObjects, logGraphEngineErrorCode, patchGraphNodeLogContext, runGraphWithLogContext, traceExecutionMemory, } from "./graphEngineLogxer.js";
|
|
34
29
|
import { runWithAiTasksStackLogging } from "@exellix/ai-tasks";
|
|
30
|
+
import { nodePlanFromFinalizerPlan, patchNodePlanMainModelFromWire, resolveRunTaskNodePlan, } from "./runTaskNodePlan.js";
|
|
35
31
|
import { assertHostJobId, newGraphRunTaskId } from "./graphRunIdentity.js";
|
|
36
32
|
import { resolveTaskKey } from "./resolveTaskKey.js";
|
|
37
33
|
import { buildPredicateEvalContextForNode, mirrorTaskVariablesOnExecution, readExecutionVariableBuckets, seedGraphVariableBucketsFromRuntime, } from "./variables.js";
|
|
@@ -367,7 +363,6 @@ export function createExellixGraphRuntime(opts) {
|
|
|
367
363
|
});
|
|
368
364
|
}
|
|
369
365
|
const wireModelConfig = toRunTaskModelConfig(effectiveModelConfig);
|
|
370
|
-
const effectiveLlmCall = buildMainLlmCallForRunTask(wireModelConfig, input.node?.taskConfiguration?.llmCall);
|
|
371
366
|
const forwardRunTaskTrace = shouldForwardRunTaskTraceMode({
|
|
372
367
|
runTaskExecutionMode: input.runTaskExecutionMode ?? opts.runTaskExecutionMode,
|
|
373
368
|
});
|
|
@@ -402,34 +397,43 @@ export function createExellixGraphRuntime(opts) {
|
|
|
402
397
|
config: finalizer.config,
|
|
403
398
|
executionMemory: execution,
|
|
404
399
|
outputsMemory,
|
|
405
|
-
runTask: (req) =>
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
400
|
+
runTask: (req) => {
|
|
401
|
+
const utilityKey = String(req.skillKey ??
|
|
402
|
+
finalizer.config?.utilityKey ??
|
|
403
|
+
"synthesize");
|
|
404
|
+
return opts.tasksClient.runTask({
|
|
405
|
+
...req,
|
|
406
|
+
agentId: input.job?.agentId ?? "standalone-agent",
|
|
407
|
+
jobTypeId: resolveJobTypeId(input.job),
|
|
408
|
+
taskTypeId: `exellix-graph-finalizer:${utilityKey}`,
|
|
409
|
+
coreSkillId: String(finalizer.id),
|
|
410
|
+
nodeId: String(finalizer.id),
|
|
411
|
+
graphId: input.graphId,
|
|
412
|
+
masterSkillId: input.graphId,
|
|
413
|
+
masterSkillActivityId: `${lifecycleJobId}:${finalizer.id}`,
|
|
414
|
+
input: req.input ?? {},
|
|
415
|
+
skillKey: utilityKey,
|
|
416
|
+
executionStrategies: [],
|
|
417
|
+
nodePlan: nodePlanFromFinalizerPlan({
|
|
418
|
+
finalizerId: String(finalizer.id),
|
|
419
|
+
utilityKey,
|
|
420
|
+
finalizerPlan: input.finalizerPlan,
|
|
421
|
+
}),
|
|
422
|
+
identity: {
|
|
423
|
+
...finalizerIdentity,
|
|
424
|
+
...(req.identity &&
|
|
425
|
+
typeof req.identity === "object" &&
|
|
426
|
+
!Array.isArray(req.identity)
|
|
427
|
+
? req.identity
|
|
428
|
+
: {}),
|
|
429
|
+
kind: "finalizer",
|
|
430
|
+
},
|
|
431
|
+
...(forwardRunTaskTrace ? { executionMode: "trace" } : {}),
|
|
432
|
+
...((input.runTaskDiagnostics ?? opts.runTaskDiagnostics) != null
|
|
433
|
+
? { diagnostics: input.runTaskDiagnostics ?? opts.runTaskDiagnostics }
|
|
422
434
|
: {}),
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
modelConfig: wireModelConfig,
|
|
426
|
-
llmCall: effectiveLlmCall,
|
|
427
|
-
executionStrategies: [],
|
|
428
|
-
...(forwardRunTaskTrace ? { executionMode: "trace" } : {}),
|
|
429
|
-
...((input.runTaskDiagnostics ?? opts.runTaskDiagnostics) != null
|
|
430
|
-
? { diagnostics: input.runTaskDiagnostics ?? opts.runTaskDiagnostics }
|
|
431
|
-
: {}),
|
|
432
|
-
}),
|
|
435
|
+
});
|
|
436
|
+
},
|
|
433
437
|
context: {
|
|
434
438
|
graphId: input.graphId,
|
|
435
439
|
jobId: input.job?.jobId,
|
|
@@ -659,34 +663,6 @@ export function createExellixGraphRuntime(opts) {
|
|
|
659
663
|
markNodeLifecycleEmitted(pe);
|
|
660
664
|
throw pe;
|
|
661
665
|
}
|
|
662
|
-
let executionPipeline;
|
|
663
|
-
try {
|
|
664
|
-
executionPipeline = resolveExecutionPipelineForTaskNode({
|
|
665
|
-
node: input.node,
|
|
666
|
-
optionsExecutionPipeline: input.graphExecutionPipeline,
|
|
667
|
-
executionExecutionPipeline: input.execution?.executionPipeline,
|
|
668
|
-
});
|
|
669
|
-
}
|
|
670
|
-
catch (pe) {
|
|
671
|
-
if (input.eventEmitter) {
|
|
672
|
-
input.eventEmitter.emit(createNodeFailEvent(lifecycleJobId, input.graphId, graphRunTaskId, input.node, skillKey, {
|
|
673
|
-
error: { message: pe?.message, code: pe?.code, stack: pe?.stack },
|
|
674
|
-
memoryAfter: { jobMemory: input.jobMemory, taskMemory: input.taskMemory, execution },
|
|
675
|
-
response: undefined,
|
|
676
|
-
}, input.jobCorrelation));
|
|
677
|
-
}
|
|
678
|
-
const err = new Error(pe?.message ?? "Execution pipeline resolution failed");
|
|
679
|
-
err.code = pe?.code ?? "INPUT_SYNTHESIS_PIPELINE_CONFLICT";
|
|
680
|
-
err.nodeId = input.node?.id;
|
|
681
|
-
markNodeLifecycleEmitted(err);
|
|
682
|
-
throw err;
|
|
683
|
-
}
|
|
684
|
-
const hasSynthesizedContextPreStep = Array.isArray(executionPipeline) &&
|
|
685
|
-
executionPipeline.some((s) => s.phase === "pre" && s.type === "synthesized-context");
|
|
686
|
-
const preStepConfig = hasSynthesizedContextPreStep && Array.isArray(executionPipeline)
|
|
687
|
-
? normalizeSynthesizedContextConfig(executionPipeline.find((s) => s.phase === "pre" && s.type === "synthesized-context")?.config)
|
|
688
|
-
: undefined;
|
|
689
|
-
const includeContextInPrompt = hasSynthesizedContextPreStep && preStepConfig?.autoEnableContext !== true;
|
|
690
666
|
const executionRec = execution;
|
|
691
667
|
mirrorTaskVariablesOnExecution({
|
|
692
668
|
execution: executionRec,
|
|
@@ -695,12 +671,6 @@ export function createExellixGraphRuntime(opts) {
|
|
|
695
671
|
});
|
|
696
672
|
const variableBuckets = readExecutionVariableBuckets(executionRec);
|
|
697
673
|
const jobVariables = variableBuckets.jobVariables;
|
|
698
|
-
const hasExistingSynthesizedContext = execution != null &&
|
|
699
|
-
typeof execution === "object" &&
|
|
700
|
-
execution.synthesizedContext != null;
|
|
701
|
-
const clearSynthForTask = input.clearSynthesizedContextPerNode === true &&
|
|
702
|
-
hasSynthesizedContextPreStep &&
|
|
703
|
-
hasExistingSynthesizedContext;
|
|
704
674
|
const nodeBindings = resolveTaskNodeInputsForRunTask({
|
|
705
675
|
node: input.node,
|
|
706
676
|
execution: executionRec,
|
|
@@ -721,51 +691,22 @@ export function createExellixGraphRuntime(opts) {
|
|
|
721
691
|
const metaTk = input.node?.taskConfiguration?.taskKind;
|
|
722
692
|
const taskKindForward = metaTk === "decision" || metaTk === "utility" || metaTk === "content" ? metaTk : undefined;
|
|
723
693
|
const autoValDec = input.node?.taskConfiguration?.autoValidateDecisionOutput;
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
aiTasks: opts.tasksClient,
|
|
732
|
-
job: input.job,
|
|
733
|
-
nodeId: String(input.node.id),
|
|
734
|
-
graphId: input.graphId,
|
|
735
|
-
taskId: graphRunTaskId,
|
|
736
|
-
runTaskJobId: lifecycleJobId,
|
|
737
|
-
execution: executionRec,
|
|
738
|
-
variables: jobVariables,
|
|
739
|
-
jobMemory: input.jobMemory,
|
|
740
|
-
taskMemory: input.taskMemory,
|
|
741
|
-
jobContext,
|
|
742
|
-
prevNodeId: input.prevNodeId,
|
|
743
|
-
modelConfig: effectiveModelConfig,
|
|
744
|
-
runTaskIdentity: runTaskIdentityBase,
|
|
745
|
-
nodeTaskConfiguration: input.node?.taskConfiguration,
|
|
746
|
-
forwardRunTaskTrace,
|
|
747
|
-
runTaskDiagnostics: (input.runTaskDiagnostics ?? opts.runTaskDiagnostics),
|
|
748
|
-
nodeTimeoutMs: input.nodeTimeoutMs,
|
|
749
|
-
});
|
|
750
|
-
if (!preRes.ok) {
|
|
751
|
-
const err = new Error(preRes.response.error?.message ?? "ENGINE_PRE_STRATEGY_FAILED");
|
|
752
|
-
err.code = preRes.response.error?.code ?? "ENGINE_PRE_STRATEGY_FAILED";
|
|
753
|
-
err.nodeId = input.node?.id;
|
|
754
|
-
if (input.eventEmitter) {
|
|
755
|
-
input.eventEmitter.emit(createNodeFailEvent(lifecycleJobId, input.graphId, graphRunTaskId, input.node, skillKey, {
|
|
756
|
-
error: {
|
|
757
|
-
message: err.message,
|
|
758
|
-
code: err.code,
|
|
759
|
-
...(preRes.response.error != null ? { details: preRes.response.error } : {}),
|
|
760
|
-
},
|
|
761
|
-
memoryAfter: { jobMemory: input.jobMemory, taskMemory: input.taskMemory, execution },
|
|
762
|
-
response: preRes.response,
|
|
763
|
-
}, input.jobCorrelation));
|
|
764
|
-
}
|
|
765
|
-
markNodeLifecycleEmitted(err);
|
|
766
|
-
throw err;
|
|
767
|
-
}
|
|
694
|
+
let runTaskNodePlan = resolveRunTaskNodePlan({
|
|
695
|
+
nodePlan: input.nodePlan,
|
|
696
|
+
skillKey,
|
|
697
|
+
nodeId: String(input.node.id),
|
|
698
|
+
});
|
|
699
|
+
if (!input.nodePlan) {
|
|
700
|
+
runTaskNodePlan = patchNodePlanMainModelFromWire(runTaskNodePlan, wireModelConfig);
|
|
768
701
|
}
|
|
702
|
+
const startedAt = Date.now();
|
|
703
|
+
const hasSynthesizedContextPreStep = runTaskNodePlan.executionUnits.some((u) => u.unitKind === "externalPreUtility" || u.unitKind === "pipelinePhase");
|
|
704
|
+
const hasExistingSynthesizedContext = execution != null &&
|
|
705
|
+
typeof execution === "object" &&
|
|
706
|
+
execution.synthesizedContext != null;
|
|
707
|
+
const clearSynthForTask = input.clearSynthesizedContextPerNode === true &&
|
|
708
|
+
hasSynthesizedContextPreStep &&
|
|
709
|
+
hasExistingSynthesizedContext;
|
|
769
710
|
const executionForTask = clearSynthForTask
|
|
770
711
|
? (() => {
|
|
771
712
|
const c = { ...executionRec };
|
|
@@ -831,7 +772,18 @@ export function createExellixGraphRuntime(opts) {
|
|
|
831
772
|
}
|
|
832
773
|
const runTaskJobMemory = mergeKnowledgePatchIntoRunTaskMemory(input.jobMemory, input.jobKnowledgePatch);
|
|
833
774
|
const runTaskTaskMemory = mergeKnowledgePatchIntoRunTaskMemory(input.taskMemory, input.taskKnowledgePatch);
|
|
834
|
-
const metaStrats =
|
|
775
|
+
const metaStrats = runTaskNodePlan.invokeContract?.pipeline &&
|
|
776
|
+
typeof runTaskNodePlan.invokeContract.pipeline === "object" &&
|
|
777
|
+
Array.isArray(runTaskNodePlan.invokeContract.pipeline.executionStrategies)
|
|
778
|
+
? runTaskNodePlan.invokeContract.pipeline
|
|
779
|
+
.executionStrategies
|
|
780
|
+
: input.node?.taskConfiguration?.executionStrategies;
|
|
781
|
+
const outputValidationFromPlan = runTaskNodePlan.invokeContract?.validation &&
|
|
782
|
+
typeof runTaskNodePlan.invokeContract.validation === "object" &&
|
|
783
|
+
"aiTasksOutputValidation" in runTaskNodePlan.invokeContract.validation
|
|
784
|
+
? runTaskNodePlan.invokeContract.validation
|
|
785
|
+
.aiTasksOutputValidation
|
|
786
|
+
: undefined;
|
|
835
787
|
const req = buildAiTasksRunTaskRequest({
|
|
836
788
|
skillKey,
|
|
837
789
|
job: input.job,
|
|
@@ -848,19 +800,16 @@ export function createExellixGraphRuntime(opts) {
|
|
|
848
800
|
executionMemory: executionForTask,
|
|
849
801
|
jobContext,
|
|
850
802
|
prevNodeId: input.prevNodeId,
|
|
851
|
-
executionPipeline: executionPipeline,
|
|
852
|
-
includeContextInPrompt: includeContextInPrompt === true ? true : undefined,
|
|
853
803
|
narrix: narrix ?? undefined,
|
|
854
804
|
...extractRunTaskStrategyOverrides(input.node?.taskConfiguration),
|
|
855
|
-
outputValidation:
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
805
|
+
outputValidation: outputValidationFromPlan ??
|
|
806
|
+
(input.node?.taskConfiguration?.aiTasksOutputValidation != null &&
|
|
807
|
+
typeof input.node.taskConfiguration.aiTasksOutputValidation === "object" &&
|
|
808
|
+
input.node.taskConfiguration.aiTasksOutputValidation !== null &&
|
|
809
|
+
"schema" in input.node.taskConfiguration.aiTasksOutputValidation
|
|
810
|
+
? input.node.taskConfiguration.aiTasksOutputValidation
|
|
811
|
+
: undefined),
|
|
861
812
|
diagnostics: (input.runTaskDiagnostics ?? opts.runTaskDiagnostics),
|
|
862
|
-
modelConfig: wireModelConfig,
|
|
863
|
-
llmCall: effectiveLlmCall,
|
|
864
813
|
identity: buildRunTaskIdentityEnvelope({
|
|
865
814
|
base: runTaskIdentityBase,
|
|
866
815
|
nodeMeta: input.node?.taskConfiguration,
|
|
@@ -875,6 +824,8 @@ export function createExellixGraphRuntime(opts) {
|
|
|
875
824
|
executionStrategies: Array.isArray(metaStrats) ? metaStrats : [],
|
|
876
825
|
xynthesized: xynthesizedOutboundForNode(executionRec, String(input.node.id)),
|
|
877
826
|
smartInput: input.node.smartInput,
|
|
827
|
+
nodePlan: runTaskNodePlan,
|
|
828
|
+
...(input.executionTrace != null ? { executionTrace: input.executionTrace } : {}),
|
|
878
829
|
});
|
|
879
830
|
// TRACE: Validate request object before sending
|
|
880
831
|
traceExecutionMemory('executeNode', 'runTask request built', {
|
|
@@ -1022,53 +973,6 @@ export function createExellixGraphRuntime(opts) {
|
|
|
1022
973
|
};
|
|
1023
974
|
// Handle execution object updates from response (patch merged above)
|
|
1024
975
|
// Note: We don't modify jobMemory or taskMemory - they're set before the job starts and passed through as-is
|
|
1025
|
-
if (strategyKeys.postStrategyKey != null) {
|
|
1026
|
-
const postExec = updatedExecution != null && typeof updatedExecution === "object" && !Array.isArray(updatedExecution)
|
|
1027
|
-
? updatedExecution
|
|
1028
|
-
: executionRec;
|
|
1029
|
-
const postRes = await runEngineAiTasksStrategyPhase({
|
|
1030
|
-
phase: "post",
|
|
1031
|
-
strategySkillKey: strategyKeys.postStrategyKey,
|
|
1032
|
-
parentSkillKey: skillKey,
|
|
1033
|
-
aiTasks: opts.tasksClient,
|
|
1034
|
-
job: input.job,
|
|
1035
|
-
nodeId: String(input.node.id),
|
|
1036
|
-
graphId: input.graphId,
|
|
1037
|
-
taskId: graphRunTaskId,
|
|
1038
|
-
runTaskJobId: lifecycleJobId,
|
|
1039
|
-
execution: postExec,
|
|
1040
|
-
variables: jobVariables,
|
|
1041
|
-
jobMemory: input.jobMemory,
|
|
1042
|
-
taskMemory: input.taskMemory,
|
|
1043
|
-
jobContext,
|
|
1044
|
-
prevNodeId: input.prevNodeId,
|
|
1045
|
-
modelConfig: effectiveModelConfig,
|
|
1046
|
-
runTaskIdentity: runTaskIdentityBase,
|
|
1047
|
-
nodeTaskConfiguration: input.node?.taskConfiguration,
|
|
1048
|
-
forwardRunTaskTrace,
|
|
1049
|
-
runTaskDiagnostics: (input.runTaskDiagnostics ?? opts.runTaskDiagnostics),
|
|
1050
|
-
nodeTimeoutMs: input.nodeTimeoutMs,
|
|
1051
|
-
});
|
|
1052
|
-
if (!postRes.ok) {
|
|
1053
|
-
const err = new Error(postRes.response.error?.message ?? "ENGINE_POST_STRATEGY_FAILED");
|
|
1054
|
-
err.code = postRes.response.error?.code ?? "ENGINE_POST_STRATEGY_FAILED";
|
|
1055
|
-
err.nodeId = input.node?.id;
|
|
1056
|
-
if (input.eventEmitter) {
|
|
1057
|
-
input.eventEmitter.emit(createNodeFailEvent(lifecycleJobId, input.graphId, graphRunTaskId, input.node, skillKey, {
|
|
1058
|
-
error: {
|
|
1059
|
-
message: err.message,
|
|
1060
|
-
code: err.code,
|
|
1061
|
-
...(postRes.response.error != null ? { details: postRes.response.error } : {}),
|
|
1062
|
-
},
|
|
1063
|
-
memoryAfter: { jobMemory: input.jobMemory, taskMemory: input.taskMemory, execution: postExec },
|
|
1064
|
-
response: postRes.response,
|
|
1065
|
-
}, input.jobCorrelation));
|
|
1066
|
-
}
|
|
1067
|
-
markNodeLifecycleEmitted(err);
|
|
1068
|
-
throw err;
|
|
1069
|
-
}
|
|
1070
|
-
updatedExecution = postExec;
|
|
1071
|
-
}
|
|
1072
976
|
// TRACE: Log execution object from response
|
|
1073
977
|
traceExecutionMemory('executeNode', 'Processing runTask response', {
|
|
1074
978
|
nodeId: input.node?.id,
|
|
@@ -1160,7 +1064,7 @@ export function createExellixGraphRuntime(opts) {
|
|
|
1160
1064
|
const { plan: suppliedPlan, runtime } = input;
|
|
1161
1065
|
const { plan } = preparePlanExecuteEntry(suppliedPlan, runtime);
|
|
1162
1066
|
const materialized = embeddedGraphToExellixGraph(plan);
|
|
1163
|
-
const graph =
|
|
1067
|
+
const graph = materialized;
|
|
1164
1068
|
const merged = mergeExellixGraphRuntimeInvocation(runtime, opts);
|
|
1165
1069
|
const scheduling = plan.schedulingPolicy;
|
|
1166
1070
|
const plannerMode = scheduling?.mode ?? runtime.mode;
|
|
@@ -1650,12 +1554,14 @@ export function createExellixGraphRuntime(opts) {
|
|
|
1650
1554
|
: nodePlanEntryResolved && node.type !== "finalizer"
|
|
1651
1555
|
? graphAiModelConfigFromNodePlan(nodePlanEntryResolved)
|
|
1652
1556
|
: undefined;
|
|
1653
|
-
const nodeExecutionPipeline = nodePlanEntryResolved != null ? executionPipelineFromNodePlan(nodePlanEntryResolved) : undefined;
|
|
1654
1557
|
const r = await executeNode({
|
|
1655
1558
|
graphId: resolvedGraphId,
|
|
1656
1559
|
graph,
|
|
1657
1560
|
graphRunTaskId: graphTaskId,
|
|
1658
1561
|
node: taskNodeForExecute,
|
|
1562
|
+
nodePlan: nodePlanEntryResolved,
|
|
1563
|
+
finalizerPlan: finalizerPlanEntryResolved,
|
|
1564
|
+
executionTrace,
|
|
1659
1565
|
job,
|
|
1660
1566
|
jobMemory: currentJobMemory,
|
|
1661
1567
|
taskMemory: nodeTaskMemory,
|
|
@@ -1669,7 +1575,6 @@ export function createExellixGraphRuntime(opts) {
|
|
|
1669
1575
|
runTaskIdentity: merged.runTaskIdentity,
|
|
1670
1576
|
runTaskExecutionMode: merged.runTaskExecutionMode,
|
|
1671
1577
|
runTaskDiagnostics: merged.runTaskDiagnostics,
|
|
1672
|
-
graphExecutionPipeline: nodeExecutionPipeline ?? merged.executionPipeline,
|
|
1673
1578
|
skillKeyResolution: merged.skillKeyResolution,
|
|
1674
1579
|
nodeTimeoutMs: merged.nodeTimeoutMs,
|
|
1675
1580
|
clearSynthesizedContextPerNode: merged.clearSynthesizedContextPerNode,
|
|
@@ -3,6 +3,7 @@ import { buildAiTasksRunTaskRequest } from './buildAiTasksRunTaskRequest.js';
|
|
|
3
3
|
import { buildRunTaskIdentityEnvelope } from './runTaskAugments.js';
|
|
4
4
|
import { runTaskResponseSucceeded } from './runTaskResponse.js';
|
|
5
5
|
import { withTimeout } from './withTimeout.js';
|
|
6
|
+
import { patchNodePlanMainModelFromWire, resolveRunTaskNodePlan } from './runTaskNodePlan.js';
|
|
6
7
|
function nonEmptyStrategyKey(v) {
|
|
7
8
|
return typeof v === 'string' && v.trim().length > 0;
|
|
8
9
|
}
|
|
@@ -31,11 +32,15 @@ export async function runEngineAiTasksStrategyPhase(args) {
|
|
|
31
32
|
const taskTypeIdOverride = args.phase === 'pre'
|
|
32
33
|
? `exellix-graph-xynthesis-pre:${args.parentSkillKey}`
|
|
33
34
|
: `exellix-graph-xynthesis-post:${args.parentSkillKey}`;
|
|
35
|
+
const wireModelConfig = toRunTaskModelConfig(args.modelConfig);
|
|
36
|
+
const runTaskNodePlan = patchNodePlanMainModelFromWire(resolveRunTaskNodePlan({
|
|
37
|
+
skillKey: args.strategySkillKey,
|
|
38
|
+
nodeId: args.nodeId,
|
|
39
|
+
}), wireModelConfig);
|
|
34
40
|
const req = buildAiTasksRunTaskRequest({
|
|
35
41
|
skillKey: args.strategySkillKey,
|
|
36
42
|
job: args.job,
|
|
37
43
|
nodeId: args.nodeId,
|
|
38
|
-
taskConfiguration: undefined,
|
|
39
44
|
graphId: args.graphId,
|
|
40
45
|
taskId: args.taskId,
|
|
41
46
|
runTaskJobId: args.runTaskJobId,
|
|
@@ -52,14 +57,13 @@ export async function runEngineAiTasksStrategyPhase(args) {
|
|
|
52
57
|
executionMemory: args.execution,
|
|
53
58
|
jobContext: args.jobContext,
|
|
54
59
|
prevNodeId: args.prevNodeId,
|
|
55
|
-
executionPipeline: [{ phase: 'main', type: 'direct' }],
|
|
56
60
|
executionStrategies: [],
|
|
57
|
-
modelConfig: toRunTaskModelConfig(args.modelConfig),
|
|
58
61
|
identity,
|
|
59
62
|
...(args.forwardRunTaskTrace ? { executionMode: 'trace' } : {}),
|
|
60
63
|
...(args.runTaskDiagnostics != null && { diagnostics: args.runTaskDiagnostics }),
|
|
61
64
|
taskKind: 'utility',
|
|
62
65
|
taskTypeIdOverride,
|
|
66
|
+
nodePlan: runTaskNodePlan,
|
|
63
67
|
});
|
|
64
68
|
const run = () => args.aiTasks.runTask(req);
|
|
65
69
|
const response = await (args.nodeTimeoutMs
|
|
@@ -7,11 +7,10 @@
|
|
|
7
7
|
* v7 closed schema: no root `executionType`, `outputConstraints`, `question`, or `jobInput`.
|
|
8
8
|
* Graph-engine forwards optional `inputs` (caller bag, as-is) separately from `input` (MAIN as-is + node bindings) — see `.docs/CR-input-and-inputs-dual-root.md`.
|
|
9
9
|
*/
|
|
10
|
-
import type {
|
|
10
|
+
import type { RunTaskRequest } from '@exellix/ai-tasks';
|
|
11
|
+
import type { GraphExecutionTraceV2, NodeExecutionPlan } from '@x12i/graphenix-executable-contracts';
|
|
11
12
|
import type { SmartInputConfig, XynthesizedMemory } from '../types/aiTasksDerivedTypes.js';
|
|
12
13
|
import type { Job } from '../types/refs.js';
|
|
13
|
-
import type { RunTaskModelConfigWire } from './graphAiModelConfig.js';
|
|
14
|
-
import type { ExecutionStepOption } from '../types/options.js';
|
|
15
14
|
import type { ResolvedNarrixWirePayload } from '../types/narrix.js';
|
|
16
15
|
/** Request/metadata keys that must never carry provider API secrets (env-only). */
|
|
17
16
|
export declare const FORBIDDEN_RUN_TASK_SECRET_KEYS: readonly ["openrouterApiKey", "OPENROUTER_API_KEY", "OPEN_ROUTER_KEY", "apiKey", "api_key", "openRouterApiKey"];
|
|
@@ -43,14 +42,9 @@ export type BuildAiTasksRunTaskRequestArgs = {
|
|
|
43
42
|
executionMemory?: Record<string, unknown>;
|
|
44
43
|
jobContext?: Record<string, unknown>;
|
|
45
44
|
prevNodeId?: string;
|
|
46
|
-
executionPipeline?: ExecutionStepOption[];
|
|
47
|
-
includeContextInPrompt?: boolean;
|
|
48
45
|
narrix?: ResolvedNarrixWirePayload;
|
|
49
46
|
outputValidation?: RunTaskRequest['outputValidation'];
|
|
50
47
|
diagnostics?: RunTaskRequest['diagnostics'];
|
|
51
|
-
/** Required on every `runTask` (@exellix/ai-tasks 8.4+). */
|
|
52
|
-
modelConfig: RunTaskModelConfigWire;
|
|
53
|
-
llmCall?: LlmCallConfig;
|
|
54
48
|
identity?: Record<string, unknown>;
|
|
55
49
|
executionMode?: 'default' | 'trace';
|
|
56
50
|
taskKind?: RunTaskRequest['taskKind'];
|
|
@@ -65,6 +59,10 @@ export type BuildAiTasksRunTaskRequestArgs = {
|
|
|
65
59
|
executionStrategies?: RunTaskRequest['executionStrategies'];
|
|
66
60
|
xynthesized?: XynthesizedMemory;
|
|
67
61
|
smartInput?: SmartInputConfig;
|
|
62
|
+
/** Frozen graphenix node plan — required for `@exellix/ai-tasks` ≥ 9 (`runTask` hot path). */
|
|
63
|
+
nodePlan: NodeExecutionPlan;
|
|
64
|
+
/** Optional graphenix v2 trace handle; ai-tasks appends unit / model invocation events. */
|
|
65
|
+
executionTrace?: GraphExecutionTraceV2;
|
|
68
66
|
};
|
|
69
67
|
export declare function resolveJobTypeId(job?: Job): string;
|
|
70
68
|
export declare function resolveTaskTypeId(skillKey: string, nodeId: string, taskConfiguration?: Record<string, unknown>): string;
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import { buildRunTaskTaskConfigurationForward } from './buildRunTaskTaskConfigurationForward.js';
|
|
2
1
|
import { normalizeSmartInputConfigForRunTask } from './smartInputPaths.js';
|
|
3
2
|
/** Request/metadata keys that must never carry provider API secrets (env-only). */
|
|
4
3
|
export const FORBIDDEN_RUN_TASK_SECRET_KEYS = [
|
|
@@ -135,11 +134,12 @@ export function buildAiTasksRunTaskRequest(args) {
|
|
|
135
134
|
const masterSkillActivityId = `${args.runTaskJobId}:${args.nodeId}`;
|
|
136
135
|
const executionStrategies = args.executionStrategies ?? [];
|
|
137
136
|
const metaPassthrough = extractRunTaskMetadataPassthrough(args.taskConfiguration);
|
|
138
|
-
const taskConfigurationForward = buildRunTaskTaskConfigurationForward(args.taskConfiguration);
|
|
139
137
|
const smartInputForward = normalizeSmartInputConfigForRunTask(args.smartInput);
|
|
140
138
|
const req = {
|
|
141
139
|
...metaPassthrough,
|
|
142
140
|
skillKey: args.skillKey,
|
|
141
|
+
nodePlan: args.nodePlan,
|
|
142
|
+
...(args.executionTrace != null ? { executionTrace: args.executionTrace } : {}),
|
|
143
143
|
jobId: args.runTaskJobId,
|
|
144
144
|
taskId: args.taskId,
|
|
145
145
|
agentId,
|
|
@@ -162,13 +162,9 @@ export function buildAiTasksRunTaskRequest(args) {
|
|
|
162
162
|
...(args.executionMemory != null ? { executionMemory: args.executionMemory } : {}),
|
|
163
163
|
...(args.jobContext != null ? { jobContext: args.jobContext } : {}),
|
|
164
164
|
...(args.prevNodeId != null && args.prevNodeId !== '' ? { prevNodeId: args.prevNodeId } : {}),
|
|
165
|
-
...(args.executionPipeline != null ? { executionPipeline: args.executionPipeline } : {}),
|
|
166
|
-
...(args.includeContextInPrompt === true ? { includeContextInPrompt: true } : {}),
|
|
167
165
|
...(args.narrix != null ? { narrix: args.narrix } : {}),
|
|
168
166
|
...(args.outputValidation != null ? { outputValidation: args.outputValidation } : {}),
|
|
169
167
|
...(args.diagnostics != null ? { diagnostics: args.diagnostics } : {}),
|
|
170
|
-
modelConfig: args.modelConfig,
|
|
171
|
-
...(args.llmCall != null ? { llmCall: args.llmCall } : {}),
|
|
172
168
|
...(args.identity != null ? { identity: args.identity } : {}),
|
|
173
169
|
...(args.executionMode != null ? { executionMode: args.executionMode } : {}),
|
|
174
170
|
...(args.taskKind != null ? { taskKind: args.taskKind } : {}),
|
|
@@ -179,7 +175,6 @@ export function buildAiTasksRunTaskRequest(args) {
|
|
|
179
175
|
executionStrategies,
|
|
180
176
|
...(args.xynthesized != null ? { xynthesized: args.xynthesized } : {}),
|
|
181
177
|
...(smartInputForward != null ? { smartInput: smartInputForward } : {}),
|
|
182
|
-
...(taskConfigurationForward != null ? { taskConfiguration: taskConfigurationForward } : {}),
|
|
183
178
|
};
|
|
184
179
|
return req;
|
|
185
180
|
}
|
|
@@ -2,15 +2,18 @@
|
|
|
2
2
|
* Host helpers for execution-matrix style orchestrators (e.g. `@exellix/exellix-runtime`).
|
|
3
3
|
*
|
|
4
4
|
* Graph-engine does not call matrix claim APIs; the host injects `executeGraph` and supplies
|
|
5
|
-
* a `{
|
|
5
|
+
* a `{ plan, runtime }` request with per-graph `GraphEntryContract` + seeded
|
|
6
6
|
* `runtime.executionMemory` objects built here.
|
|
7
7
|
*/
|
|
8
|
+
import type { AuthoringGraphDocument } from '@x12i/graphenix-executable-contracts';
|
|
8
9
|
import type { Graph, GraphEntryContract, GraphEntryExecutionInputSpec, Job } from '../types/refs.js';
|
|
9
10
|
import type { ExellixGraphRuntimeOptions, ExecuteGraphInput, ExecuteGraphResult, GraphRuntimeObject } from './ExellixGraphRuntime.js';
|
|
10
11
|
import type { GraphLoader } from './ExellixGraphRuntime.js';
|
|
12
|
+
export { resolveGraphEntryFromAuthoringDocument, authoringDocumentGraphId } from '../compile/authoringDocumentHelpers.js';
|
|
11
13
|
/**
|
|
12
14
|
* Reads Layer 01 contract from the canonical graph document (`metadata.graphEntry`).
|
|
13
|
-
*
|
|
15
|
+
* For execute-time materialized {@link Graph} (from plan). Authoring loaders should use
|
|
16
|
+
* {@link resolveGraphEntryFromAuthoringDocument}.
|
|
14
17
|
*/
|
|
15
18
|
export declare function resolveGraphEntryFromGraph(graph: Graph): GraphEntryContract | undefined;
|
|
16
19
|
/**
|
|
@@ -47,7 +50,7 @@ export type BuildExecutionSeedResult = {
|
|
|
47
50
|
export declare function buildExecutionSeedFromGraphEntry(graphEntry: GraphEntryContract | undefined, sources?: BuildExecutionSeedSources): BuildExecutionSeedResult;
|
|
48
51
|
/** Builds the canonical graph-engine execution request for matrix-style hosts. */
|
|
49
52
|
export declare function buildGraphExecutionRequest(input: {
|
|
50
|
-
|
|
53
|
+
doc: AuthoringGraphDocument;
|
|
51
54
|
runtime: GraphRuntimeObject;
|
|
52
55
|
}): ExecuteGraphInput;
|
|
53
56
|
/**
|
|
@@ -2,10 +2,10 @@
|
|
|
2
2
|
* Host helpers for execution-matrix style orchestrators (e.g. `@exellix/exellix-runtime`).
|
|
3
3
|
*
|
|
4
4
|
* Graph-engine does not call matrix claim APIs; the host injects `executeGraph` and supplies
|
|
5
|
-
* a `{
|
|
5
|
+
* a `{ plan, runtime }` request with per-graph `GraphEntryContract` + seeded
|
|
6
6
|
* `runtime.executionMemory` objects built here.
|
|
7
7
|
*/
|
|
8
|
-
import { compileExellixExecutablePlan } from '../
|
|
8
|
+
import { compileExellixExecutablePlan } from '../compile/compileExellixExecutablePlan.js';
|
|
9
9
|
import { mergeGraphDocumentModel } from '../types/refs.js';
|
|
10
10
|
import { createExellixGraphRuntime } from './ExellixGraphRuntime.js';
|
|
11
11
|
import { selectByPath, writeByPath } from './pathExpr.js';
|
|
@@ -15,9 +15,11 @@ function isExecutionInputSpec(spec) {
|
|
|
15
15
|
function isValueInputSpec(spec) {
|
|
16
16
|
return spec.kind !== 'execution' && typeof spec.path === 'string';
|
|
17
17
|
}
|
|
18
|
+
export { resolveGraphEntryFromAuthoringDocument, authoringDocumentGraphId } from '../compile/authoringDocumentHelpers.js';
|
|
18
19
|
/**
|
|
19
20
|
* Reads Layer 01 contract from the canonical graph document (`metadata.graphEntry`).
|
|
20
|
-
*
|
|
21
|
+
* For execute-time materialized {@link Graph} (from plan). Authoring loaders should use
|
|
22
|
+
* {@link resolveGraphEntryFromAuthoringDocument}.
|
|
21
23
|
*/
|
|
22
24
|
export function resolveGraphEntryFromGraph(graph) {
|
|
23
25
|
const meta = mergeGraphDocumentModel(graph);
|
|
@@ -77,7 +79,7 @@ export function buildExecutionSeedFromGraphEntry(graphEntry, sources = {}) {
|
|
|
77
79
|
/** Builds the canonical graph-engine execution request for matrix-style hosts. */
|
|
78
80
|
export function buildGraphExecutionRequest(input) {
|
|
79
81
|
return {
|
|
80
|
-
plan: compileExellixExecutablePlan(input.
|
|
82
|
+
plan: compileExellixExecutablePlan(input.doc, input.runtime),
|
|
81
83
|
runtime: input.runtime,
|
|
82
84
|
};
|
|
83
85
|
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import type { FinalizerExecutionPlan, NodeExecutionPlan } from '@x12i/graphenix-executable-contracts';
|
|
2
|
+
import type { RunTaskModelConfigWire } from './graphAiModelConfig.js';
|
|
3
|
+
/** Resolve the frozen node plan required by `@exellix/ai-tasks` ≥ 9. */
|
|
4
|
+
export declare function resolveRunTaskNodePlan(args: {
|
|
5
|
+
nodePlan?: NodeExecutionPlan;
|
|
6
|
+
skillKey: string;
|
|
7
|
+
nodeId: string;
|
|
8
|
+
}): NodeExecutionPlan;
|
|
9
|
+
/** Standalone {@link executeNode} without compile: patch MAIN unit selection from resolved graph profiles. */
|
|
10
|
+
export declare function patchNodePlanMainModelFromWire(plan: NodeExecutionPlan, wire: RunTaskModelConfigWire): NodeExecutionPlan;
|
|
11
|
+
export declare function nodePlanFromFinalizerPlan(args: {
|
|
12
|
+
finalizerId: string;
|
|
13
|
+
utilityKey: string;
|
|
14
|
+
finalizerPlan?: FinalizerExecutionPlan;
|
|
15
|
+
}): NodeExecutionPlan;
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { minimalNodePlanForSkillKey } from '@exellix/ai-tasks';
|
|
2
|
+
function mainSkillUnit(plan) {
|
|
3
|
+
return plan.executionUnits.find((u) => u.unitKind === 'mainSkill');
|
|
4
|
+
}
|
|
5
|
+
function selectionFromWireSlot(value) {
|
|
6
|
+
if (typeof value !== 'string' || value.trim().length === 0)
|
|
7
|
+
return undefined;
|
|
8
|
+
return { kind: 'profileChoice', key: value.trim() };
|
|
9
|
+
}
|
|
10
|
+
/** Resolve the frozen node plan required by `@exellix/ai-tasks` ≥ 9. */
|
|
11
|
+
export function resolveRunTaskNodePlan(args) {
|
|
12
|
+
return args.nodePlan ?? minimalNodePlanForSkillKey(args.skillKey, args.nodeId);
|
|
13
|
+
}
|
|
14
|
+
/** Standalone {@link executeNode} without compile: patch MAIN unit selection from resolved graph profiles. */
|
|
15
|
+
export function patchNodePlanMainModelFromWire(plan, wire) {
|
|
16
|
+
const next = structuredClone(plan);
|
|
17
|
+
const main = mainSkillUnit(next);
|
|
18
|
+
const selection = selectionFromWireSlot(wire.skillModel);
|
|
19
|
+
if (main && selection) {
|
|
20
|
+
main.modelSelection = selection;
|
|
21
|
+
main.modelSlot = 'skillModel';
|
|
22
|
+
}
|
|
23
|
+
return next;
|
|
24
|
+
}
|
|
25
|
+
export function nodePlanFromFinalizerPlan(args) {
|
|
26
|
+
const slots = args.finalizerPlan?.modelSlots;
|
|
27
|
+
const plan = minimalNodePlanForSkillKey(args.utilityKey, args.finalizerId);
|
|
28
|
+
if (!slots)
|
|
29
|
+
return plan;
|
|
30
|
+
const main = mainSkillUnit(plan);
|
|
31
|
+
if (!main)
|
|
32
|
+
return plan;
|
|
33
|
+
const selection = slots.postActionModel?.selection ??
|
|
34
|
+
slots.skillModel?.selection ??
|
|
35
|
+
slots.preActionModel?.selection;
|
|
36
|
+
if (selection) {
|
|
37
|
+
main.modelSelection = selection;
|
|
38
|
+
main.modelSlot =
|
|
39
|
+
slots.postActionModel?.selection != null
|
|
40
|
+
? 'postActionModel'
|
|
41
|
+
: slots.skillModel?.selection != null
|
|
42
|
+
? 'skillModel'
|
|
43
|
+
: 'preActionModel';
|
|
44
|
+
}
|
|
45
|
+
return plan;
|
|
46
|
+
}
|