8726 workflow add a test button in workflow code step (#9016)

- add test button to workflow code step
- add test tab to workflow code step


https://github.com/user-attachments/assets/e180a827-7321-49a2-8026-88490c557da2



![image](https://github.com/user-attachments/assets/cacbd756-de3f-4141-a84c-8e1853f6556b)

![image](https://github.com/user-attachments/assets/ee170d81-8a22-4178-bd6d-11a0e8c73365)
This commit is contained in:
martmull
2024-12-13 11:16:29 +01:00
committed by GitHub
parent 07aaf0801c
commit b10d831371
95 changed files with 1537 additions and 1611 deletions

View File

@ -0,0 +1,44 @@
import { InputSchema } from '@/workflow/types/InputSchema';
import { getDefaultFunctionInputFromInputSchema } from '@/serverless-functions/utils/getDefaultFunctionInputFromInputSchema';
describe('getDefaultFunctionInputFromInputSchema', () => {
it('should init function input properly', () => {
const inputSchema = [
{
type: 'object',
properties: {
a: {
type: 'string',
},
b: {
type: 'number',
},
c: {
type: 'array',
items: { type: 'string' },
},
d: {
type: 'object',
properties: {
da: { type: 'string', enum: ['my', 'enum'] },
db: { type: 'number' },
},
},
e: { type: 'object' },
},
},
] as InputSchema;
const expectedResult = [
{
a: null,
b: null,
c: [],
d: { da: 'my', db: null },
e: {},
},
];
expect(getDefaultFunctionInputFromInputSchema(inputSchema)).toEqual(
expectedResult,
);
});
});

View File

@ -0,0 +1,50 @@
import { getFunctionInputFromSourceCode } from '@/serverless-functions/utils/getFunctionInputFromSourceCode';
describe('getFunctionInputFromSourceCode', () => {
it('should return empty input if not parameter', () => {
const fileContent = 'function testFunction() { return }';
const result = getFunctionInputFromSourceCode(fileContent);
expect(result).toEqual({});
});
it('should return first input if multiple parameters', () => {
const fileContent =
'function testFunction(params1: {}, params2: {}) { return }';
const result = getFunctionInputFromSourceCode(fileContent);
expect(result).toEqual({});
});
it('should return empty input if wrong parameter', () => {
const fileContent = 'function testFunction(params: string) { return }';
const result = getFunctionInputFromSourceCode(fileContent);
expect(result).toEqual({});
});
it('should return input from source code', () => {
const fileContent = `
function testFunction(
params: {
param1: string;
param2: number;
param3: boolean;
param4: object;
param5: { subParam1: string };
param6: "my" | "enum";
param7: string[];
}
): void {
return
}
`;
const result = getFunctionInputFromSourceCode(fileContent);
expect(result).toEqual({
param1: null,
param2: null,
param3: null,
param4: {},
param5: {
subParam1: null,
},
param6: 'my',
param7: [],
});
});
});

View File

@ -0,0 +1,67 @@
import { getFunctionInputSchema } from '@/serverless-functions/utils/getFunctionInputSchema';
describe('getFunctionInputSchema', () => {
it('should analyze a simple function correctly', () => {
const fileContent = `
function testFunction(param1: string, param2: number): void {
return;
}
`;
const result = getFunctionInputSchema(fileContent);
expect(result).toEqual([{ type: 'string' }, { type: 'number' }]);
});
it('should analyze a arrow function correctly', () => {
const fileContent = `
export const main = async (
param1: string,
param2: number,
): Promise<object> => {
return param1;
};
`;
const result = getFunctionInputSchema(fileContent);
expect(result).toEqual([{ type: 'string' }, { type: 'number' }]);
});
it('should analyze a complex function correctly', () => {
const fileContent = `
function testFunction(
params: {
param1: string;
param2: number;
param3: boolean;
param4: object;
param5: { subParam1: string };
param6: "my" | "enum";
param7: string[];
}
): void {
return
}
`;
const result = getFunctionInputSchema(fileContent);
expect(result).toEqual([
{
type: 'object',
properties: {
param1: { type: 'string' },
param2: { type: 'number' },
param3: { type: 'boolean' },
param4: { type: 'object' },
param5: {
type: 'object',
properties: {
subParam1: { type: 'string' },
},
},
param6: { type: 'string', enum: ['my', 'enum'] },
param7: { type: 'array', items: { type: 'string' } },
},
},
]);
});
});

View File

@ -0,0 +1,24 @@
import { getFunctionOutputSchema } from '@/serverless-functions/utils/getFunctionOutputSchema';
describe('getFunctionOutputSchema', () => {
it('should compute outputSchema properly', () => {
const testResult = {
a: null,
b: 'b',
c: { cc: 1 },
d: true,
e: [1, 2, 3],
};
const expectedOutputSchema = {
a: { isLeaf: true, type: 'unknown', value: null },
b: { isLeaf: true, type: 'string', value: 'b' },
c: {
isLeaf: false,
value: { cc: { isLeaf: true, type: 'number', value: 1 } },
},
d: { isLeaf: true, type: 'boolean', value: true },
e: { isLeaf: true, type: 'array', value: [1, 2, 3] },
};
expect(getFunctionOutputSchema(testResult)).toEqual(expectedOutputSchema);
});
});

View File

@ -0,0 +1,27 @@
import { mergeDefaultFunctionInputAndFunctionInput } from '../mergeDefaultFunctionInputAndFunctionInput';
describe('mergeDefaultFunctionInputAndFunctionInput', () => {
it('should merge properly', () => {
const newInput = {
a: null,
b: null,
c: { cc: null },
d: null,
e: { ee: null },
};
const oldInput = { a: 'a', c: 'c', d: { da: null }, e: { ee: 'ee' } };
const expectedResult = {
a: 'a',
b: null,
c: { cc: null },
d: null,
e: { ee: 'ee' },
};
expect(
mergeDefaultFunctionInputAndFunctionInput({
newInput: newInput,
oldInput: oldInput,
}),
).toEqual(expectedResult);
});
});