( definition: WorkflowDefinition, options: WorkflowSchedulerOptions, )
| 46 | } |
| 47 | |
| 48 | export async function runWorkflowWithScheduler( |
| 49 | definition: WorkflowDefinition, |
| 50 | options: WorkflowSchedulerOptions, |
| 51 | ): Promise<void> { |
| 52 | const { run, onNodeSkipped } = options; |
| 53 | |
| 54 | // Map sourceRef -> List of Edges (preserving handle info) |
| 55 | const successEdges = new Map<string, WorkflowEdge[]>(); |
| 56 | const failureDependents = new Map<string, string[]>(); |
| 57 | |
| 58 | const successParentsMap = new Map<string, Set<string>>(); |
| 59 | const failureParentsMap = new Map<string, Set<string>>(); |
| 60 | |
| 61 | for (const edge of definition.edges ?? []) { |
| 62 | if (edge.kind === 'error') { |
| 63 | const children = failureDependents.get(edge.sourceRef) ?? []; |
| 64 | children.push(edge.targetRef); |
| 65 | failureDependents.set(edge.sourceRef, children); |
| 66 | |
| 67 | const parents = failureParentsMap.get(edge.targetRef) ?? new Set<string>(); |
| 68 | parents.add(edge.sourceRef); |
| 69 | failureParentsMap.set(edge.targetRef, parents); |
| 70 | } else { |
| 71 | const edges = successEdges.get(edge.sourceRef) ?? []; |
| 72 | edges.push(edge); |
| 73 | successEdges.set(edge.sourceRef, edges); |
| 74 | |
| 75 | const parents = successParentsMap.get(edge.targetRef) ?? new Set<string>(); |
| 76 | parents.add(edge.sourceRef); |
| 77 | successParentsMap.set(edge.targetRef, parents); |
| 78 | } |
| 79 | } |
| 80 | |
| 81 | const nodeStates = new Map<string, NodeState>(); |
| 82 | const readyQueue: ReadyItem[] = []; |
| 83 | const pending = new Set<string>(); |
| 84 | |
| 85 | for (const action of definition.actions) { |
| 86 | pending.add(action.ref); |
| 87 | |
| 88 | const successParents = new Set(successParentsMap.get(action.ref) ?? []); |
| 89 | const failureParents = new Set(failureParentsMap.get(action.ref) ?? []); |
| 90 | |
| 91 | const metadata = definition.nodes?.[action.ref]; |
| 92 | const strategy: WorkflowJoinStrategy | 'all' = metadata?.joinStrategy ?? 'all'; |
| 93 | |
| 94 | const state: NodeState = { |
| 95 | strategy, |
| 96 | successParents, |
| 97 | skippedParents: new Set(), |
| 98 | failureParents, |
| 99 | triggeredBySuccess: successParents.size === 0, |
| 100 | failureTriggered: false, |
| 101 | skipped: false, |
| 102 | totalSuccessParents: successParents.size, |
| 103 | }; |
| 104 | |
| 105 | nodeStates.set(action.ref, state); |
no test coverage detected