mirror of
https://github.com/n8n-io/n8n.git
synced 2025-01-05 09:57:27 -08:00
382 lines
11 KiB
TypeScript
382 lines
11 KiB
TypeScript
import { Container } from 'typedi';
|
|
|
|
import type { TestDefinition } from '@/databases/entities/test-definition.ee';
|
|
import type { User } from '@/databases/entities/user';
|
|
import type { WorkflowEntity } from '@/databases/entities/workflow-entity';
|
|
import { TestDefinitionRepository } from '@/databases/repositories/test-definition.repository.ee';
|
|
import { TestMetricRepository } from '@/databases/repositories/test-metric.repository.ee';
|
|
import { createUserShell } from '@test-integration/db/users';
|
|
import { createWorkflow } from '@test-integration/db/workflows';
|
|
import * as testDb from '@test-integration/test-db';
|
|
import type { SuperAgentTest } from '@test-integration/types';
|
|
import * as utils from '@test-integration/utils';
|
|
|
|
let authOwnerAgent: SuperAgentTest;
|
|
let workflowUnderTest: WorkflowEntity;
|
|
let otherWorkflow: WorkflowEntity;
|
|
let testDefinition: TestDefinition;
|
|
let otherTestDefinition: TestDefinition;
|
|
let ownerShell: User;
|
|
|
|
const testServer = utils.setupTestServer({ endpointGroups: ['evaluation'] });
|
|
|
|
beforeAll(async () => {
|
|
ownerShell = await createUserShell('global:owner');
|
|
authOwnerAgent = testServer.authAgentFor(ownerShell);
|
|
});
|
|
|
|
beforeEach(async () => {
|
|
await testDb.truncate(['TestDefinition', 'TestMetric']);
|
|
|
|
workflowUnderTest = await createWorkflow({ name: 'workflow-under-test' }, ownerShell);
|
|
|
|
testDefinition = Container.get(TestDefinitionRepository).create({
|
|
name: 'test',
|
|
workflow: { id: workflowUnderTest.id },
|
|
});
|
|
await Container.get(TestDefinitionRepository).save(testDefinition);
|
|
|
|
otherWorkflow = await createWorkflow({ name: 'other-workflow' });
|
|
|
|
otherTestDefinition = Container.get(TestDefinitionRepository).create({
|
|
name: 'other-test',
|
|
workflow: { id: otherWorkflow.id },
|
|
});
|
|
await Container.get(TestDefinitionRepository).save(otherTestDefinition);
|
|
});
|
|
|
|
describe('GET /evaluation/test-definitions/:testDefinitionId/metrics', () => {
|
|
test('should retrieve empty list of metrics for a test definition', async () => {
|
|
const resp = await authOwnerAgent.get(
|
|
`/evaluation/test-definitions/${testDefinition.id}/metrics`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(200);
|
|
expect(resp.body.data.length).toBe(0);
|
|
});
|
|
|
|
test('should retrieve metrics for a test definition', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const newMetric2 = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-2',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric2);
|
|
|
|
const resp = await authOwnerAgent.get(
|
|
`/evaluation/test-definitions/${testDefinition.id}/metrics`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(200);
|
|
expect(resp.body.data.length).toBe(2);
|
|
expect(resp.body.data).toEqual(
|
|
expect.arrayContaining([
|
|
expect.objectContaining({
|
|
id: expect.any(String),
|
|
name: 'metric-1',
|
|
}),
|
|
expect.objectContaining({
|
|
id: expect.any(String),
|
|
name: 'metric-2',
|
|
}),
|
|
]),
|
|
);
|
|
});
|
|
|
|
test('should return 404 if test definition does not exist', async () => {
|
|
const resp = await authOwnerAgent.get('/evaluation/test-definitions/999/metrics');
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
|
|
test('should return 404 if test definition is not accessible to the user', async () => {
|
|
const resp = await authOwnerAgent.get(
|
|
`/evaluation/test-definitions/${otherTestDefinition.id}/metrics`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
});
|
|
|
|
describe('GET /evaluation/test-definitions/:testDefinitionId/metrics/:id', () => {
|
|
test('should retrieve a metric for a test definition', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent.get(
|
|
`/evaluation/test-definitions/${testDefinition.id}/metrics/${newMetric.id}`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(200);
|
|
expect(resp.body.data).toEqual(
|
|
expect.objectContaining({
|
|
id: newMetric.id,
|
|
name: 'metric-1',
|
|
}),
|
|
);
|
|
});
|
|
|
|
test('should return 404 if metric does not exist', async () => {
|
|
const resp = await authOwnerAgent.get(
|
|
`/evaluation/test-definitions/${testDefinition.id}/metrics/999`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
|
|
test('should return 404 if metric is not accessible to the user', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: otherTestDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent.get(
|
|
`/evaluation/test-definitions/${otherTestDefinition.id}/metrics/${newMetric.id}`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
});
|
|
|
|
describe('POST /evaluation/test-definitions/:testDefinitionId/metrics', () => {
|
|
test('should create a metric for a test definition', async () => {
|
|
const resp = await authOwnerAgent
|
|
.post(`/evaluation/test-definitions/${testDefinition.id}/metrics`)
|
|
.send({
|
|
name: 'metric-1',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(200);
|
|
expect(resp.body.data).toEqual(
|
|
expect.objectContaining({
|
|
id: expect.any(String),
|
|
name: 'metric-1',
|
|
}),
|
|
);
|
|
|
|
const metrics = await Container.get(TestMetricRepository).find({
|
|
where: { testDefinition: { id: testDefinition.id } },
|
|
});
|
|
expect(metrics.length).toBe(1);
|
|
expect(metrics[0].name).toBe('metric-1');
|
|
});
|
|
|
|
test('should return 400 if name is missing', async () => {
|
|
const resp = await authOwnerAgent
|
|
.post(`/evaluation/test-definitions/${testDefinition.id}/metrics`)
|
|
.send({});
|
|
|
|
expect(resp.statusCode).toBe(400);
|
|
expect(resp.body.errors).toEqual(
|
|
expect.arrayContaining([
|
|
expect.objectContaining({
|
|
code: 'invalid_type',
|
|
message: 'Required',
|
|
path: ['name'],
|
|
}),
|
|
]),
|
|
);
|
|
});
|
|
|
|
test('should return 400 if name is not a string', async () => {
|
|
const resp = await authOwnerAgent
|
|
.post(`/evaluation/test-definitions/${testDefinition.id}/metrics`)
|
|
.send({
|
|
name: 123,
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(400);
|
|
expect(resp.body.errors).toEqual(
|
|
expect.arrayContaining([
|
|
expect.objectContaining({
|
|
code: 'invalid_type',
|
|
message: 'Expected string, received number',
|
|
path: ['name'],
|
|
}),
|
|
]),
|
|
);
|
|
});
|
|
|
|
test('should return 404 if test definition does not exist', async () => {
|
|
const resp = await authOwnerAgent.post('/evaluation/test-definitions/999/metrics').send({
|
|
name: 'metric-1',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
|
|
test('should return 404 if test definition is not accessible to the user', async () => {
|
|
const resp = await authOwnerAgent
|
|
.post(`/evaluation/test-definitions/${otherTestDefinition.id}/metrics`)
|
|
.send({
|
|
name: 'metric-1',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
});
|
|
|
|
describe('PATCH /evaluation/test-definitions/:testDefinitionId/metrics/:id', () => {
|
|
test('should update a metric for a test definition', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent
|
|
.patch(`/evaluation/test-definitions/${testDefinition.id}/metrics/${newMetric.id}`)
|
|
.send({
|
|
name: 'metric-2',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(200);
|
|
expect(resp.body.data).toEqual(
|
|
expect.objectContaining({
|
|
id: newMetric.id,
|
|
name: 'metric-2',
|
|
}),
|
|
);
|
|
|
|
const metrics = await Container.get(TestMetricRepository).find({
|
|
where: { testDefinition: { id: testDefinition.id } },
|
|
});
|
|
expect(metrics.length).toBe(1);
|
|
expect(metrics[0].name).toBe('metric-2');
|
|
});
|
|
|
|
test('should return 400 if name is missing', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent
|
|
.patch(`/evaluation/test-definitions/${testDefinition.id}/metrics/${newMetric.id}`)
|
|
.send({});
|
|
|
|
expect(resp.statusCode).toBe(400);
|
|
expect(resp.body.errors).toEqual(
|
|
expect.arrayContaining([
|
|
expect.objectContaining({
|
|
code: 'invalid_type',
|
|
message: 'Required',
|
|
path: ['name'],
|
|
}),
|
|
]),
|
|
);
|
|
});
|
|
|
|
test('should return 400 if name is not a string', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent
|
|
.patch(`/evaluation/test-definitions/${testDefinition.id}/metrics/${newMetric.id}`)
|
|
.send({
|
|
name: 123,
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(400);
|
|
expect(resp.body.errors).toEqual(
|
|
expect.arrayContaining([
|
|
expect.objectContaining({
|
|
code: 'invalid_type',
|
|
message: 'Expected string, received number',
|
|
}),
|
|
]),
|
|
);
|
|
});
|
|
|
|
test('should return 404 if metric does not exist', async () => {
|
|
const resp = await authOwnerAgent
|
|
.patch(`/evaluation/test-definitions/${testDefinition.id}/metrics/999`)
|
|
.send({
|
|
name: 'metric-1',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
|
|
test('should return 404 if test definition does not exist', async () => {
|
|
const resp = await authOwnerAgent.patch('/evaluation/test-definitions/999/metrics/999').send({
|
|
name: 'metric-1',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
|
|
test('should return 404 if metric is not accessible to the user', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: otherTestDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent
|
|
.patch(`/evaluation/test-definitions/${otherTestDefinition.id}/metrics/${newMetric.id}`)
|
|
.send({
|
|
name: 'metric-2',
|
|
});
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
});
|
|
|
|
describe('DELETE /evaluation/test-definitions/:testDefinitionId/metrics/:id', () => {
|
|
test('should delete a metric for a test definition', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: testDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent.delete(
|
|
`/evaluation/test-definitions/${testDefinition.id}/metrics/${newMetric.id}`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(200);
|
|
expect(resp.body.data).toEqual({ success: true });
|
|
|
|
const metrics = await Container.get(TestMetricRepository).find({
|
|
where: { testDefinition: { id: testDefinition.id } },
|
|
});
|
|
expect(metrics.length).toBe(0);
|
|
});
|
|
|
|
test('should return 404 if metric does not exist', async () => {
|
|
const resp = await authOwnerAgent.delete(
|
|
`/evaluation/test-definitions/${testDefinition.id}/metrics/999`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
|
|
test('should return 404 if metric is not accessible to the user', async () => {
|
|
const newMetric = Container.get(TestMetricRepository).create({
|
|
testDefinition: { id: otherTestDefinition.id },
|
|
name: 'metric-1',
|
|
});
|
|
await Container.get(TestMetricRepository).save(newMetric);
|
|
|
|
const resp = await authOwnerAgent.delete(
|
|
`/evaluation/test-definitions/${otherTestDefinition.id}/metrics/${newMetric.id}`,
|
|
);
|
|
|
|
expect(resp.statusCode).toBe(404);
|
|
});
|
|
});
|