import { mock } from 'vitest-mock-extended'; import type { INode, ExecutionError } from '../src/interfaces'; import { createRunExecutionData, createEmptyRunExecutionData, createErrorExecutionData, type CreateFullRunExecutionDataOptions, } from '../src/run-execution-data-factory'; describe('RunExecutionDataFactory', () => { describe('createRunExecutionData', () => { it('should create a complete IRunExecutionData object with default values', () => { const result = createRunExecutionData(); expect(result).toEqual({ version: 1, startData: {}, manualData: undefined, parentExecution: undefined, pushRef: undefined, validateSignature: undefined, waitTill: undefined, resultData: { error: undefined, runData: {}, pinData: undefined, lastNodeExecuted: undefined, metadata: undefined, }, executionData: { contextData: {}, nodeExecutionStack: [], metadata: {}, waitingExecution: {}, waitingExecutionSource: {}, }, }); }); it('should create a complete IRunExecutionData object with custom options', () => { const options = { startData: { startNodes: [{ name: 'Start', sourceData: { previousNode: 'Previous' } }], destinationNode: { nodeName: 'End', mode: 'inclusive' }, }, resultData: { runData: { testNode: [] }, lastNodeExecuted: 'testNode', }, executionData: { nodeExecutionStack: [{ node: {} as INode, data: {}, source: null }], runtimeData: { version: 1 as const, establishedAt: 1234567890, source: 'webhook' as const, credentials: 'test-credentials', }, }, parentExecution: { executionId: 'parent-123', workflowId: 'workflow-456', }, validateSignature: true, waitTill: new Date('2023-01-01'), } satisfies CreateFullRunExecutionDataOptions; const result = createRunExecutionData(options); expect(result.startData).toEqual(options.startData); expect(result.resultData.runData).toEqual(options.resultData.runData); expect(result.resultData.lastNodeExecuted).toEqual(options.resultData.lastNodeExecuted); expect(result.executionData?.nodeExecutionStack).toEqual( options.executionData.nodeExecutionStack, ); expect(result.executionData?.runtimeData).toEqual(options.executionData.runtimeData); expect(result.parentExecution).toEqual(options.parentExecution); expect(result.validateSignature).toBe(true); expect(result.waitTill).toEqual(options.waitTill); }); it('should omit `executionData` if null is passed', () => { const result = createRunExecutionData({ executionData: null, }); expect(result.executionData).toBeUndefined(); expect(result.startData).toEqual({}); expect(result.resultData.runData).toEqual({}); }); it('should omit `resultData.runData` if null is passed', () => { const result = createRunExecutionData({ resultData: { runData: null, }, }); expect(result.resultData.runData).toBeUndefined(); expect(result.startData).toEqual({}); expect(result.executionData).toEqual({ contextData: {}, nodeExecutionStack: [], metadata: {}, waitingExecution: {}, waitingExecutionSource: {}, }); }); }); describe('createMinimalRunExecutionData', () => { it('should create a minimal IRunExecutionData object with empty runData', () => { const result = createEmptyRunExecutionData(); expect(result).toEqual({ version: 1, resultData: { runData: {}, }, }); }); }); describe('createErrorExecutionData', () => { it('should create a IRunExecutionData object for error execution', () => { const node: INode = { id: 'node-123', name: 'TestNode', type: 'test', typeVersion: 1, position: [0, 0], parameters: {}, }; const error = mock({ message: 'Test error occurred', name: 'TestError', }); const result = createErrorExecutionData(node, error); expect(result.startData?.destinationNode).toEqual({ nodeName: 'TestNode', mode: 'inclusive', }); expect(result.startData?.runNodeFilter).toEqual(['TestNode']); expect(result.executionData?.contextData).toEqual({}); expect(result.executionData?.metadata).toEqual({}); expect(result.executionData?.waitingExecution).toEqual({}); expect(result.executionData?.waitingExecutionSource).toEqual({}); expect(result.executionData?.nodeExecutionStack).toHaveLength(1); expect(result.executionData?.nodeExecutionStack?.[0]?.node).toBe(node); expect(result.executionData?.nodeExecutionStack?.[0]?.data.main).toEqual([ [{ json: {}, pairedItem: { item: 0 } }], ]); expect(result.executionData?.nodeExecutionStack?.[0]?.source).toBe(null); expect(result.resultData.runData['TestNode']).toHaveLength(1); expect(result.resultData.runData['TestNode'][0]).toEqual({ startTime: 0, executionIndex: 0, executionTime: 0, error, source: [], }); expect(result.resultData.error).toBe(error); expect(result.resultData.lastNodeExecuted).toBe('TestNode'); }); }); });