refactor(core): Add more unit tests for Workflow.ts (no-changelog) (#9868)

Co-authored-by: Danny Martini <danny@n8n.io>
This commit is contained in:
कारतोफ्फेलस्क्रिप्ट™ 2024-06-27 11:20:59 +02:00 committed by GitHub
parent e25682ddad
commit 9454a851bb
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 438 additions and 310 deletions

View file

@ -63,6 +63,18 @@ function dedupe<T>(arr: T[]): T[] {
return [...new Set(arr)]; return [...new Set(arr)];
} }
export interface WorkflowParameters {
id?: string;
name?: string;
nodes: INode[];
connections: IConnections;
active: boolean;
nodeTypes: INodeTypes;
staticData?: IDataObject;
settings?: IWorkflowSettings;
pinData?: IPinData;
}
export class Workflow { export class Workflow {
id: string; id: string;
@ -90,18 +102,7 @@ export class Workflow {
pinData?: IPinData; pinData?: IPinData;
// constructor(id: string | undefined, nodes: INode[], connections: IConnections, active: boolean, nodeTypes: INodeTypes, staticData?: IDataObject, settings?: IWorkflowSettings) { constructor(parameters: WorkflowParameters) {
constructor(parameters: {
id?: string;
name?: string;
nodes: INode[];
connections: IConnections;
active: boolean;
nodeTypes: INodeTypes;
staticData?: IDataObject;
settings?: IWorkflowSettings;
pinData?: IPinData;
}) {
this.id = parameters.id as string; // @tech_debt Ensure this is not optional this.id = parameters.id as string; // @tech_debt Ensure this is not optional
this.name = parameters.name; this.name = parameters.name;
this.nodeTypes = parameters.nodeTypes; this.nodeTypes = parameters.nodeTypes;
@ -251,16 +252,14 @@ export class Workflow {
* is fine. If there are issues it returns the issues * is fine. If there are issues it returns the issues
* which have been found for the different nodes. * which have been found for the different nodes.
* TODO: Does currently not check for credential issues! * TODO: Does currently not check for credential issues!
*
*/ */
checkReadyForExecution(inputData: { checkReadyForExecution(
startNode?: string; inputData: {
destinationNode?: string; startNode?: string;
pinDataNodeNames?: string[]; destinationNode?: string;
}): IWorkflowIssues | null { pinDataNodeNames?: string[];
let node: INode; } = {},
let nodeType: INodeType | undefined; ): IWorkflowIssues | null {
let nodeIssues: INodeIssues | null = null;
const workflowIssues: IWorkflowIssues = {}; const workflowIssues: IWorkflowIssues = {};
let checkNodes: string[] = []; let checkNodes: string[] = [];
@ -277,14 +276,14 @@ export class Workflow {
} }
for (const nodeName of checkNodes) { for (const nodeName of checkNodes) {
nodeIssues = null; let nodeIssues: INodeIssues | null = null;
node = this.nodes[nodeName]; const node = this.nodes[nodeName];
if (node.disabled === true) { if (node.disabled === true) {
continue; continue;
} }
nodeType = this.nodeTypes.getByNameAndVersion(node.type, node.typeVersion); const nodeType = this.nodeTypes.getByNameAndVersion(node.type, node.typeVersion);
if (nodeType === undefined) { if (nodeType === undefined) {
// Node type is not known // Node type is not known

View file

@ -1,3 +1,5 @@
import { mock } from 'jest-mock-extended';
import { NodeConnectionType } from '@/Interfaces';
import type { import type {
IBinaryKeyData, IBinaryKeyData,
IConnections, IConnections,
@ -5,10 +7,14 @@ import type {
INode, INode,
INodeExecutionData, INodeExecutionData,
INodeParameters, INodeParameters,
INodeType,
INodeTypeDescription,
INodeTypes,
IRunExecutionData, IRunExecutionData,
NodeParameterValueType, NodeParameterValueType,
} from '@/Interfaces'; } from '@/Interfaces';
import { Workflow } from '@/Workflow'; import { Workflow, type WorkflowParameters } from '@/Workflow';
import * as NodeHelpers from '@/NodeHelpers';
process.env.TEST_VARIABLE_1 = 'valueEnvVariable1'; process.env.TEST_VARIABLE_1 = 'valueEnvVariable1';
@ -20,303 +26,426 @@ interface StubNode {
} }
describe('Workflow', () => { describe('Workflow', () => {
describe('renameNodeInParameterValue for expressions', () => { describe('checkIfWorkflowCanBeActivated', () => {
const tests = [ const disabledNode = mock<INode>({ type: 'triggerNode', disabled: true });
{ const unknownNode = mock<INode>({ type: 'unknownNode' });
description: 'do nothing if there is no expression', const noTriggersNode = mock<INode>({ type: 'noTriggersNode' });
input: { const pollNode = mock<INode>({ type: 'pollNode' });
currentName: 'Node1', const triggerNode = mock<INode>({ type: 'triggerNode' });
newName: 'Node1New', const webhookNode = mock<INode>({ type: 'webhookNode' });
parameters: {
const nodeTypes = mock<INodeTypes>();
nodeTypes.getByNameAndVersion.mockImplementation((type) => {
// TODO: getByNameAndVersion signature needs to be updated to allow returning undefined
if (type === 'unknownNode') return undefined as unknown as INodeType;
const partial: Partial<INodeType> = {
poll: undefined,
trigger: undefined,
webhook: undefined,
description: mock<INodeTypeDescription>({
properties: [],
}),
};
if (type === 'pollNode') partial.poll = jest.fn();
if (type === 'triggerNode') partial.trigger = jest.fn();
if (type === 'webhookNode') partial.webhook = jest.fn();
return mock(partial);
});
test.each([
['should skip disabled nodes', disabledNode, [], false],
['should skip nodes marked as ignored', triggerNode, ['triggerNode'], false],
['should skip unknown nodes', unknownNode, [], false],
['should skip nodes with no trigger method', noTriggersNode, [], false],
['should activate if poll method exists', pollNode, [], true],
['should activate if trigger method exists', triggerNode, [], true],
['should activate if webhook method exists', webhookNode, [], true],
])('%s', async (_, node, ignoredNodes, expected) => {
const params = mock<WorkflowParameters>({ nodeTypes });
params.nodes = [node];
const workflow = new Workflow(params);
expect(workflow.checkIfWorkflowCanBeActivated(ignoredNodes)).toBe(expected);
});
});
describe('checkReadyForExecution', () => {
const disabledNode = mock<INode>({ name: 'Disabled Node', disabled: true });
const startNode = mock<INode>({ name: 'Start Node' });
const unknownNode = mock<INode>({ name: 'Unknown Node', type: 'unknownNode' });
const nodeParamIssuesSpy = jest.spyOn(NodeHelpers, 'getNodeParametersIssues');
const nodeTypes = mock<INodeTypes>();
nodeTypes.getByNameAndVersion.mockImplementation((type) => {
// TODO: getByNameAndVersion signature needs to be updated to allow returning undefined
if (type === 'unknownNode') return undefined as unknown as INodeType;
return mock<INodeType>({
description: {
properties: [],
},
});
});
beforeEach(() => jest.clearAllMocks());
it('should return null if there are no nodes', () => {
const workflow = new Workflow({
nodes: [],
connections: {},
active: false,
nodeTypes,
});
const issues = workflow.checkReadyForExecution();
expect(issues).toBe(null);
expect(nodeTypes.getByNameAndVersion).not.toHaveBeenCalled();
expect(nodeParamIssuesSpy).not.toHaveBeenCalled();
});
it('should return null if there are no enabled nodes', () => {
const workflow = new Workflow({
nodes: [disabledNode],
connections: {},
active: false,
nodeTypes,
});
const issues = workflow.checkReadyForExecution({ startNode: disabledNode.name });
expect(issues).toBe(null);
expect(nodeTypes.getByNameAndVersion).toHaveBeenCalledTimes(1);
expect(nodeParamIssuesSpy).not.toHaveBeenCalled();
});
it('should return typeUnknown for unknown nodes', () => {
const workflow = new Workflow({
nodes: [unknownNode],
connections: {},
active: false,
nodeTypes,
});
const issues = workflow.checkReadyForExecution({ startNode: unknownNode.name });
expect(issues).toEqual({ [unknownNode.name]: { typeUnknown: true } });
expect(nodeTypes.getByNameAndVersion).toHaveBeenCalledTimes(2);
expect(nodeParamIssuesSpy).not.toHaveBeenCalled();
});
it('should return issues for regular nodes', () => {
const workflow = new Workflow({
nodes: [startNode],
connections: {},
active: false,
nodeTypes,
});
nodeParamIssuesSpy.mockReturnValue({ execution: false });
const issues = workflow.checkReadyForExecution({ startNode: startNode.name });
expect(issues).toEqual({ [startNode.name]: { execution: false } });
expect(nodeTypes.getByNameAndVersion).toHaveBeenCalledTimes(2);
expect(nodeParamIssuesSpy).toHaveBeenCalled();
});
});
describe('renameNodeInParameterValue', () => {
describe('for expressions', () => {
const tests = [
{
description: 'do nothing if there is no expression',
input: {
currentName: 'Node1',
newName: 'Node1New',
parameters: {
value1: 'value1Node1',
value2: 'value2Node1',
},
},
output: {
value1: 'value1Node1', value1: 'value1Node1',
value2: 'value2Node1', value2: 'value2Node1',
}, },
}, },
output: { {
value1: 'value1Node1', description: 'should work with dot notation',
value2: 'value2Node1', input: {
}, currentName: 'Node1',
}, newName: 'NewName',
{ parameters: {
description: 'should work with dot notation', value1: "={{$node.Node1.data.value1 + 'Node1'}}",
input: { value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
currentName: 'Node1', },
newName: 'NewName', },
parameters: { output: {
value1: "={{$node.Node1.data.value1 + 'Node1'}}", value1: "={{$node.NewName.data.value1 + 'Node1'}}",
value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}", value2: "={{$node.NewName.data.value2 + ' - ' + $node.NewName.data.value2}}",
}, },
}, },
output: { {
value1: "={{$node.NewName.data.value1 + 'Node1'}}", description: 'should work with ["nodeName"]',
value2: "={{$node.NewName.data.value2 + ' - ' + $node.NewName.data.value2}}", input: {
}, currentName: 'Node1',
}, newName: 'NewName',
{ parameters: {
description: 'should work with ["nodeName"]', value1: '={{$node["Node1"]["data"]["value1"] + \'Node1\'}}',
input: { value2:
currentName: 'Node1', '={{$node["Node1"]["data"]["value2"] + \' - \' + $node["Node1"]["data"]["value2"]}}',
newName: 'NewName', },
parameters: { },
value1: '={{$node["Node1"]["data"]["value1"] + \'Node1\'}}', output: {
value1: '={{$node["NewName"]["data"]["value1"] + \'Node1\'}}',
value2: value2:
'={{$node["Node1"]["data"]["value2"] + \' - \' + $node["Node1"]["data"]["value2"]}}', '={{$node["NewName"]["data"]["value2"] + \' - \' + $node["NewName"]["data"]["value2"]}}',
}, },
}, },
output: { {
value1: '={{$node["NewName"]["data"]["value1"] + \'Node1\'}}', description: 'should work with $("Node1")',
value2: input: {
'={{$node["NewName"]["data"]["value2"] + \' - \' + $node["NewName"]["data"]["value2"]}}', currentName: 'Node1',
}, newName: 'NewName',
}, parameters: {
{ value1: '={{$("Node1")["data"]["value1"] + \'Node1\'}}',
description: 'should work with $("Node1")', value2: '={{$("Node1")["data"]["value2"] + \' - \' + $("Node1")["data"]["value2"]}}',
input: { },
currentName: 'Node1',
newName: 'NewName',
parameters: {
value1: '={{$("Node1")["data"]["value1"] + \'Node1\'}}',
value2: '={{$("Node1")["data"]["value2"] + \' - \' + $("Node1")["data"]["value2"]}}',
}, },
}, output: {
output: { value1: '={{$("NewName")["data"]["value1"] + \'Node1\'}}',
value1: '={{$("NewName")["data"]["value1"] + \'Node1\'}}',
value2: '={{$("NewName")["data"]["value2"] + \' - \' + $("NewName")["data"]["value2"]}}',
},
},
{
description: 'should work with $items("Node1")',
input: {
currentName: 'Node1',
newName: 'NewName',
parameters: {
value1: '={{$items("Node1")["data"]["value1"] + \'Node1\'}}',
value2: value2:
'={{$items("Node1")["data"]["value2"] + \' - \' + $items("Node1")["data"]["value2"]}}', '={{$("NewName")["data"]["value2"] + \' - \' + $("NewName")["data"]["value2"]}}',
}, },
}, },
output: { {
value1: '={{$items("NewName")["data"]["value1"] + \'Node1\'}}', description: 'should work with $items("Node1")',
value2: input: {
'={{$items("NewName")["data"]["value2"] + \' - \' + $items("NewName")["data"]["value2"]}}', currentName: 'Node1',
}, newName: 'NewName',
}, parameters: {
{ value1: '={{$items("Node1")["data"]["value1"] + \'Node1\'}}',
description: 'should work with $items("Node1", 0, 1)', value2:
input: { '={{$items("Node1")["data"]["value2"] + \' - \' + $items("Node1")["data"]["value2"]}}',
currentName: 'Node1', },
newName: 'NewName', },
parameters: { output: {
value1: '={{$items("Node1", 0, 1)["data"]["value1"] + \'Node1\'}}', value1: '={{$items("NewName")["data"]["value1"] + \'Node1\'}}',
value2: value2:
'={{$items("Node1", 0, 1)["data"]["value2"] + \' - \' + $items("Node1", 0, 1)["data"]["value2"]}}', '={{$items("NewName")["data"]["value2"] + \' - \' + $items("NewName")["data"]["value2"]}}',
}, },
}, },
output: { {
value1: '={{$items("NewName", 0, 1)["data"]["value1"] + \'Node1\'}}', description: 'should work with $items("Node1", 0, 1)',
value2: input: {
'={{$items("NewName", 0, 1)["data"]["value2"] + \' - \' + $items("NewName", 0, 1)["data"]["value2"]}}', currentName: 'Node1',
}, newName: 'NewName',
}, parameters: {
{ value1: '={{$items("Node1", 0, 1)["data"]["value1"] + \'Node1\'}}',
description: 'should work with dot notation that contains space and special character', value2:
input: { '={{$items("Node1", 0, 1)["data"]["value2"] + \' - \' + $items("Node1", 0, 1)["data"]["value2"]}}',
currentName: 'Node1', },
newName: 'New $ Name',
parameters: {
value1: "={{$node.Node1.data.value1 + 'Node1'}}",
value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
}, },
}, output: {
output: { value1: '={{$items("NewName", 0, 1)["data"]["value1"] + \'Node1\'}}',
value1: '={{$node["New $ Name"].data.value1 + \'Node1\'}}',
value2:
'={{$node["New $ Name"].data.value2 + \' - \' + $node["New $ Name"].data.value2}}',
},
},
{
description: 'should work with dot notation that contains space and trailing $',
input: {
currentName: 'Node1',
newName: 'NewName$',
parameters: {
value1: "={{$node.Node1.data.value1 + 'Node1'}}",
value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
},
},
output: {
value1: '={{$node["NewName$"].data.value1 + \'Node1\'}}',
value2: '={{$node["NewName$"].data.value2 + \' - \' + $node["NewName$"].data.value2}}',
},
},
{
description: 'should work with dot notation that contains space and special character',
input: {
currentName: 'Node1',
newName: 'NewName $ $& $` $$$',
parameters: {
value1: "={{$node.Node1.data.value1 + 'Node1'}}",
value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
},
},
output: {
value1: '={{$node["NewName $ $& $` $$$"].data.value1 + \'Node1\'}}',
value2:
'={{$node["NewName $ $& $` $$$"].data.value2 + \' - \' + $node["NewName $ $& $` $$$"].data.value2}}',
},
},
{
description: 'should work with dot notation without trailing dot',
input: {
currentName: 'Node1',
newName: 'NewName',
parameters: {
value1: "={{$node.Node1 + 'Node1'}}",
value2: "={{$node.Node1 + ' - ' + $node.Node1}}",
},
},
output: {
value1: "={{$node.NewName + 'Node1'}}",
value2: "={{$node.NewName + ' - ' + $node.NewName}}",
},
},
{
description: "should work with ['nodeName']",
input: {
currentName: 'Node1',
newName: 'NewName',
parameters: {
value1: "={{$node['Node1']['data']['value1'] + 'Node1'}}",
value2: value2:
"={{$node['Node1']['data']['value2'] + ' - ' + $node['Node1']['data']['value2']}}", '={{$items("NewName", 0, 1)["data"]["value2"] + \' - \' + $items("NewName", 0, 1)["data"]["value2"]}}',
}, },
}, },
output: { {
value1: "={{$node['NewName']['data']['value1'] + 'Node1'}}", description: 'should work with dot notation that contains space and special character',
value2: input: {
"={{$node['NewName']['data']['value2'] + ' - ' + $node['NewName']['data']['value2']}}", currentName: 'Node1',
newName: 'New $ Name',
parameters: {
value1: "={{$node.Node1.data.value1 + 'Node1'}}",
value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
},
},
output: {
value1: '={{$node["New $ Name"].data.value1 + \'Node1\'}}',
value2:
'={{$node["New $ Name"].data.value2 + \' - \' + $node["New $ Name"].data.value2}}',
},
}, },
}, {
{ description: 'should work with dot notation that contains space and trailing $',
description: 'should work on lower levels', input: {
input: { currentName: 'Node1',
currentName: 'Node1', newName: 'NewName$',
newName: 'NewName', parameters: {
parameters: { value1: "={{$node.Node1.data.value1 + 'Node1'}}",
level1a: "={{$node.Node1.data.value1 + 'Node1'}}", value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
},
},
output: {
value1: '={{$node["NewName$"].data.value1 + \'Node1\'}}',
value2: '={{$node["NewName$"].data.value2 + \' - \' + $node["NewName$"].data.value2}}',
},
},
{
description: 'should work with dot notation that contains space and special character',
input: {
currentName: 'Node1',
newName: 'NewName $ $& $` $$$',
parameters: {
value1: "={{$node.Node1.data.value1 + 'Node1'}}",
value2: "={{$node.Node1.data.value2 + ' - ' + $node.Node1.data.value2}}",
},
},
output: {
value1: '={{$node["NewName $ $& $` $$$"].data.value1 + \'Node1\'}}',
value2:
'={{$node["NewName $ $& $` $$$"].data.value2 + \' - \' + $node["NewName $ $& $` $$$"].data.value2}}',
},
},
{
description: 'should work with dot notation without trailing dot',
input: {
currentName: 'Node1',
newName: 'NewName',
parameters: {
value1: "={{$node.Node1 + 'Node1'}}",
value2: "={{$node.Node1 + ' - ' + $node.Node1}}",
},
},
output: {
value1: "={{$node.NewName + 'Node1'}}",
value2: "={{$node.NewName + ' - ' + $node.NewName}}",
},
},
{
description: "should work with ['nodeName']",
input: {
currentName: 'Node1',
newName: 'NewName',
parameters: {
value1: "={{$node['Node1']['data']['value1'] + 'Node1'}}",
value2:
"={{$node['Node1']['data']['value2'] + ' - ' + $node['Node1']['data']['value2']}}",
},
},
output: {
value1: "={{$node['NewName']['data']['value1'] + 'Node1'}}",
value2:
"={{$node['NewName']['data']['value2'] + ' - ' + $node['NewName']['data']['value2']}}",
},
},
{
description: 'should work on lower levels',
input: {
currentName: 'Node1',
newName: 'NewName',
parameters: {
level1a: "={{$node.Node1.data.value1 + 'Node1'}}",
level1b: [
{
value2a: "={{$node.Node1.data.value1 + 'Node1'}}",
value2b: "={{$node.Node1.data.value1 + 'Node1'}}",
},
],
level1c: {
value2a: {
value3a: "={{$node.Node1.data.value1 + 'Node1'}}",
value3b: [
{
value4a: "={{$node.Node1.data.value1 + 'Node1'}}",
value4b: {
value5a: "={{$node.Node1.data.value1 + 'Node1'}}",
value5b: "={{$node.Node1.data.value1 + 'Node1'}}",
},
},
],
},
},
} as INodeParameters,
},
output: {
level1a: "={{$node.NewName.data.value1 + 'Node1'}}",
level1b: [ level1b: [
{ {
value2a: "={{$node.Node1.data.value1 + 'Node1'}}", value2a: "={{$node.NewName.data.value1 + 'Node1'}}",
value2b: "={{$node.Node1.data.value1 + 'Node1'}}", value2b: "={{$node.NewName.data.value1 + 'Node1'}}",
}, },
], ],
level1c: { level1c: {
value2a: { value2a: {
value3a: "={{$node.Node1.data.value1 + 'Node1'}}", value3a: "={{$node.NewName.data.value1 + 'Node1'}}",
value3b: [ value3b: [
{ {
value4a: "={{$node.Node1.data.value1 + 'Node1'}}", value4a: "={{$node.NewName.data.value1 + 'Node1'}}",
value4b: { value4b: {
value5a: "={{$node.Node1.data.value1 + 'Node1'}}", value5a: "={{$node.NewName.data.value1 + 'Node1'}}",
value5b: "={{$node.Node1.data.value1 + 'Node1'}}", value5b: "={{$node.NewName.data.value1 + 'Node1'}}",
}, },
}, },
], ],
}, },
}, },
} as INodeParameters,
},
output: {
level1a: "={{$node.NewName.data.value1 + 'Node1'}}",
level1b: [
{
value2a: "={{$node.NewName.data.value1 + 'Node1'}}",
value2b: "={{$node.NewName.data.value1 + 'Node1'}}",
},
],
level1c: {
value2a: {
value3a: "={{$node.NewName.data.value1 + 'Node1'}}",
value3b: [
{
value4a: "={{$node.NewName.data.value1 + 'Node1'}}",
value4b: {
value5a: "={{$node.NewName.data.value1 + 'Node1'}}",
value5b: "={{$node.NewName.data.value1 + 'Node1'}}",
},
},
],
},
}, },
}, },
}, ];
];
const nodeTypes = Helpers.NodeTypes(); const nodeTypes = Helpers.NodeTypes();
const workflow = new Workflow({ nodes: [], connections: {}, active: false, nodeTypes }); const workflow = new Workflow({ nodes: [], connections: {}, active: false, nodeTypes });
for (const testData of tests) { for (const testData of tests) {
test(testData.description, () => { test(testData.description, () => {
const result = workflow.renameNodeInParameterValue( const result = workflow.renameNodeInParameterValue(
testData.input.parameters, testData.input.parameters,
testData.input.currentName, testData.input.currentName,
testData.input.newName, testData.input.newName,
); );
expect(result).toEqual(testData.output); expect(result).toEqual(testData.output);
}); });
} }
});
describe('renameNodeInParameterValue for node with renamable content', () => {
const tests = [
{
description: "should work with $('name')",
input: {
currentName: 'Old',
newName: 'New',
parameters: { jsCode: "$('Old').first();" },
},
output: { jsCode: "$('New').first();" },
},
{
description: "should work with $node['name'] and $node.name",
input: {
currentName: 'Old',
newName: 'New',
parameters: { jsCode: "$node['Old'].first(); $node.Old.first();" },
},
output: { jsCode: "$node['New'].first(); $node.New.first();" },
},
{
description: 'should work with $items()',
input: {
currentName: 'Old',
newName: 'New',
parameters: { jsCode: "$items('Old').first();" },
},
output: { jsCode: "$items('New').first();" },
},
];
const workflow = new Workflow({
nodes: [],
connections: {},
active: false,
nodeTypes: Helpers.NodeTypes(),
}); });
for (const t of tests) { describe('for node with renamable content', () => {
test(t.description, () => { const tests = [
expect( {
workflow.renameNodeInParameterValue( description: "should work with $('name')",
t.input.parameters, input: {
t.input.currentName, currentName: 'Old',
t.input.newName, newName: 'New',
{ hasRenamableContent: true }, parameters: { jsCode: "$('Old').first();" },
), },
).toEqual(t.output); output: { jsCode: "$('New').first();" },
},
{
description: "should work with $node['name'] and $node.name",
input: {
currentName: 'Old',
newName: 'New',
parameters: { jsCode: "$node['Old'].first(); $node.Old.first();" },
},
output: { jsCode: "$node['New'].first(); $node.New.first();" },
},
{
description: 'should work with $items()',
input: {
currentName: 'Old',
newName: 'New',
parameters: { jsCode: "$items('Old').first();" },
},
output: { jsCode: "$items('New').first();" },
},
];
const workflow = new Workflow({
nodes: [],
connections: {},
active: false,
nodeTypes: Helpers.NodeTypes(),
}); });
}
for (const t of tests) {
test(t.description, () => {
expect(
workflow.renameNodeInParameterValue(
t.input.parameters,
t.input.currentName,
t.input.newName,
{ hasRenamableContent: true },
),
).toEqual(t.output);
});
}
});
}); });
describe('renameNode', () => { describe('renameNode', () => {
@ -377,7 +506,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node2', node: 'Node2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -408,7 +537,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node2', node: 'Node2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -444,7 +573,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node2', node: 'Node2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -475,7 +604,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node2New', node: 'Node2New',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -532,7 +661,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node3', node: 'Node3',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -543,12 +672,12 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node3', node: 'Node3',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
{ {
node: 'Node5', node: 'Node5',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -559,12 +688,12 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node4', node: 'Node4',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
{ {
node: 'Node5', node: 'Node5',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -616,7 +745,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node3New', node: 'Node3New',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -627,12 +756,12 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node3New', node: 'Node3New',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
{ {
node: 'Node5', node: 'Node5',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -643,12 +772,12 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node4', node: 'Node4',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
{ {
node: 'Node5', node: 'Node5',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1229,7 +1358,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node2', node: 'Node2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1240,7 +1369,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node3', node: 'Node3',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1251,7 +1380,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Node2', node: 'Node2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1521,7 +1650,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set', node: 'Set',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1532,7 +1661,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set1', node: 'Set1',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1591,21 +1720,21 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set1', node: 'Set1',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
[ [
{ {
node: 'Set', node: 'Set',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
[ [
{ {
node: 'Set', node: 'Set',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1616,7 +1745,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set2', node: 'Set2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1627,7 +1756,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set2', node: 'Set2',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1691,7 +1820,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set', node: 'Set',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1699,7 +1828,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Switch', node: 'Switch',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1710,7 +1839,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set1', node: 'Set1',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1721,12 +1850,12 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set1', node: 'Set1',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
{ {
node: 'Switch', node: 'Switch',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],
@ -1737,7 +1866,7 @@ describe('Workflow', () => {
[ [
{ {
node: 'Set1', node: 'Set1',
type: 'main', type: NodeConnectionType.Main,
index: 0, index: 0,
}, },
], ],