diff --git a/packages/cli/src/WorkflowCredentials.ts b/packages/cli/src/WorkflowCredentials.ts deleted file mode 100644 index f7f915d32cf59..0000000000000 --- a/packages/cli/src/WorkflowCredentials.ts +++ /dev/null @@ -1,51 +0,0 @@ -import Container from 'typedi'; -import { ApplicationError, type INode, type IWorkflowCredentials } from 'n8n-workflow'; -import { CredentialsRepository } from '@db/repositories/credentials.repository'; - -// eslint-disable-next-line @typescript-eslint/naming-convention -export async function WorkflowCredentials(nodes: INode[]): Promise { - // Go through all nodes to find which credentials are needed to execute the workflow - const returnCredentials: IWorkflowCredentials = {}; - - let node; - let type; - let nodeCredentials; - let foundCredentials; - - for (node of nodes) { - if (node.disabled === true || !node.credentials) { - continue; - } - - for (type of Object.keys(node.credentials)) { - if (!returnCredentials[type]) { - returnCredentials[type] = {}; - } - nodeCredentials = node.credentials[type]; - - if (!nodeCredentials.id) { - throw new ApplicationError( - `Credentials with name "${nodeCredentials.name}" for type "${type}" miss an ID.`, - { extra: { credentialName: nodeCredentials.name }, tags: { credentialType: type } }, - ); - } - - if (!returnCredentials[type][nodeCredentials.id]) { - foundCredentials = await Container.get(CredentialsRepository).findOneBy({ - id: nodeCredentials.id, - type, - }); - if (!foundCredentials) { - throw new ApplicationError('Could not find credential.', { - tags: { credentialType: type }, - extra: { credentialId: nodeCredentials.id }, - }); - } - - returnCredentials[type][nodeCredentials.id] = foundCredentials; - } - } - } - - return returnCredentials; -} diff --git a/packages/cli/test/integration/credentials.controller.test.ts b/packages/cli/test/integration/credentials.controller.test.ts index 12aa5231c4a93..3c122f2b4eb7f 100644 --- a/packages/cli/test/integration/credentials.controller.test.ts +++ b/packages/cli/test/integration/credentials.controller.test.ts @@ -1,4 +1,4 @@ -import type { Credentials } from '@/requests'; +import type { ListQuery } from '@/requests'; import type { User } from '@db/entities/User'; import * as testDb from './shared/testDb'; import { setupTestServer } from './shared/utils/'; @@ -21,7 +21,7 @@ beforeEach(async () => { member = await createMember(); }); -type GetAllResponse = { body: { data: Credentials.WithOwnedByAndSharedWith[] } }; +type GetAllResponse = { body: { data: ListQuery.Credentials.WithOwnedByAndSharedWith[] } }; describe('GET /credentials', () => { describe('should return', () => { @@ -278,7 +278,7 @@ describe('GET /credentials', () => { }); }); -function validateCredential(credential: Credentials.WithOwnedByAndSharedWith) { +function validateCredential(credential: ListQuery.Credentials.WithOwnedByAndSharedWith) { const { name, type, nodesAccess, sharedWith, ownedBy } = credential; expect(typeof name).toBe('string'); diff --git a/packages/cli/test/integration/database/repositories/execution.repository.test.ts b/packages/cli/test/integration/database/repositories/execution.repository.test.ts index 62cb57d2b8ac5..72ebaa95969b5 100644 --- a/packages/cli/test/integration/database/repositories/execution.repository.test.ts +++ b/packages/cli/test/integration/database/repositories/execution.repository.test.ts @@ -24,6 +24,7 @@ describe('ExecutionRepository', () => { const executionId = await executionRepo.createNewExecution({ workflowId: workflow.id, data: { + //@ts-expect-error This is not needed for tests resultData: {}, }, workflowData: workflow, diff --git a/packages/cli/test/unit/CredentialsHelper.test.ts b/packages/cli/test/unit/CredentialsHelper.test.ts index 648fa28918304..19be100b02b84 100644 --- a/packages/cli/test/unit/CredentialsHelper.test.ts +++ b/packages/cli/test/unit/CredentialsHelper.test.ts @@ -271,6 +271,7 @@ describe('CredentialsHelper', () => { for (const testData of tests) { test(testData.description, async () => { + //@ts-expect-error `loadedCredentials` is a getter and we are replacing it here with a property mockNodesAndCredentials.loadedCredentials = { [testData.input.credentialType.name]: { type: testData.input.credentialType, diff --git a/packages/cli/test/unit/InternalHooks.test.ts b/packages/cli/test/unit/InternalHooks.test.ts index 8d33fd4672f74..e91759daddb7c 100644 --- a/packages/cli/test/unit/InternalHooks.test.ts +++ b/packages/cli/test/unit/InternalHooks.test.ts @@ -41,6 +41,7 @@ describe('InternalHooks', () => { licensePlanName, licenseTenantId, binary_data_s3: false, + multi_main_setup_enabled: false, }; const parameters = { diff --git a/packages/cli/test/unit/Telemetry.test.ts b/packages/cli/test/unit/Telemetry.test.ts index d943d83e500c9..25f4a808675b0 100644 --- a/packages/cli/test/unit/Telemetry.test.ts +++ b/packages/cli/test/unit/Telemetry.test.ts @@ -48,7 +48,7 @@ describe('Telemetry', () => { const postHog = new PostHogClient(instanceSettings); await postHog.init(); - telemetry = new Telemetry(mock(), postHog, mock(), instanceSettings); + telemetry = new Telemetry(mock(), postHog, mock(), instanceSettings, mock()); (telemetry as any).rudderStack = mockRudderStack; }); diff --git a/packages/cli/test/unit/WorkflowCredentials.test.ts b/packages/cli/test/unit/WorkflowCredentials.test.ts deleted file mode 100644 index 504848dd51ee3..0000000000000 --- a/packages/cli/test/unit/WorkflowCredentials.test.ts +++ /dev/null @@ -1,147 +0,0 @@ -import type { FindOptionsWhere } from 'typeorm'; -import type { INode } from 'n8n-workflow'; -import { WorkflowCredentials } from '@/WorkflowCredentials'; -import type { CredentialsEntity } from '@db/entities/CredentialsEntity'; -import { CredentialsRepository } from '@db/repositories/credentials.repository'; -import { mockInstance } from '../shared/mocking'; - -const credentialsRepository = mockInstance(CredentialsRepository); -credentialsRepository.findOneBy.mockImplementation( - async (where: FindOptionsWhere) => { - const { id, type } = where as { - id: string; - type: string; - }; - // Simple statement that maps a return value based on the `id` parameter - if (id === notFoundNode.credentials!.test.id) { - return null; - } - - // Otherwise just build some kind of credential object and return it - return { - [type]: { - [id]: { - id, - name: type, - type, - nodesAccess: [], - data: '', - }, - }, - } as unknown as CredentialsEntity; - }, -); - -// Create an array of Nodes with info that pass or fail the checks as required. -// DB returns an object of type { [id: string]: ICredentialsEncrypted } but as it isn't checked -// All the mock will need to return is some form of Object when successful - -describe('WorkflowCredentials', () => { - afterEach(() => { - jest.clearAllMocks(); - }); - - test('Should return an error if any node has no credential ID', async () => { - const credentials = noIdNode.credentials!.test; - const expectedError = new Error( - `Credentials with name "${credentials.name}" for type "test" miss an ID.`, - ); - await expect(WorkflowCredentials([noIdNode])).rejects.toEqual(expectedError); - expect(credentialsRepository.findOneBy).toHaveBeenCalledTimes(0); - }); - - test('Should return an error if credentials cannot be found in the DB', async () => { - const expectedError = new Error('Could not find credential.'); - await expect(WorkflowCredentials([notFoundNode])).rejects.toEqual(expectedError); - expect(credentialsRepository.findOneBy).toHaveBeenCalledTimes(1); - }); - - test('Should ignore duplicates', async () => { - const response = await WorkflowCredentials([validNode, validNode, validNode]); - expect(Object.keys(response)).toEqual(['test']); - }); - - test('Should ignore Nodes with no credentials set', async () => { - const response = await WorkflowCredentials([validNode, noCredentialsNode]); - expect(Object.keys(response)).toEqual(['test']); - }); - - test('Should work for Nodes with multiple credentials', async () => { - const response = await WorkflowCredentials([multiCredNode]); - expect(Object.keys(response)).toEqual(['mcTest', 'mcTest2']); - }); -}); - -const validNode: INode = { - id: '1', - name: 'Node with Valid Credentials', - typeVersion: 1, - type: '', - position: [0, 0], - credentials: { - test: { - id: 'cred#1', - name: 'Test Credentials', - }, - }, - parameters: {}, -}; - -const noIdNode: INode = { - id: '2', - name: 'Node with no Credential ID', - typeVersion: 1, - type: '', - position: [0, 0], - credentials: { - test: { - id: null, - name: 'NOFIND', - }, - }, - parameters: {}, -}; - -const notFoundNode: INode = { - id: '3', - name: 'Node that will not be found in the DB', - typeVersion: 1, - type: '', - position: [0, 0], - credentials: { - test: { - id: 'noDB', - name: 'Not in Database', - }, - }, - parameters: {}, -}; - -const noCredentialsNode: INode = { - id: '4', - name: 'Node that has no credentials', - typeVersion: 1, - type: '', - position: [0, 0], - parameters: {}, -}; - -// Reference this as a DataObject so I can provide a null credential for testing -const multiCredNode: INode = { - id: '5', - name: 'Node that has mutliple credential elements', - typeVersion: 1, - type: '', - position: [0, 0], - credentials: { - mcTest: { - id: 'multicred#1', - name: 'First of Multiple Credentials', - }, - mcTest2: { - id: 'multicred#2', - name: 'Second of Multiple Credentials', - }, - }, - parameters: {}, -};