From 72d5f00185ba888fa5334a8a573fd40e26404c4e Mon Sep 17 00:00:00 2001 From: paolo-rechia Date: Mon, 21 Mar 2022 17:45:54 +0100 Subject: [PATCH 1/5] Implements PayPal Auth API Test --- .../nodes-base/nodes/PayPal/PayPal.node.ts | 59 ++++++++++++ .../PayPal.node.testCredentials.test.js | 93 +++++++++++++++++++ 2 files changed, 152 insertions(+) create mode 100644 packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js diff --git a/packages/nodes-base/nodes/PayPal/PayPal.node.ts b/packages/nodes-base/nodes/PayPal/PayPal.node.ts index f72cffde6648b..ac1adf8758e6d 100644 --- a/packages/nodes-base/nodes/PayPal/PayPal.node.ts +++ b/packages/nodes-base/nodes/PayPal/PayPal.node.ts @@ -1,8 +1,14 @@ +import { + OptionsWithUri +} from 'request'; import { IExecuteFunctions, } from 'n8n-core'; import { IDataObject, + ICredentialTestFunctions, + ICredentialsDecrypted, + INodeCredentialTestResult, INodeExecutionData, INodeType, INodeTypeDescription, @@ -46,6 +52,7 @@ export class PayPal implements INodeType { { name: 'payPalApi', required: true, + testedBy: 'payPalApiTest' }, ], properties: [ @@ -168,5 +175,57 @@ export class PayPal implements INodeType { } } return [this.helpers.returnJsonArray(returnData)]; + } + methods = { + credentialTest: { + async payPalApiTest(this: ICredentialTestFunctions, credential: ICredentialsDecrypted): Promise { + const credentials = credential.data; + const clientId = credentials!.clientId + const clientSecret = credentials!.secret + const environment = credentials!.env + + if (!clientId || !clientSecret || !environment) { + return { + status: 'Error', + message: `Connection details not valid: missing credentials` + }; + } + + let baseUrl = "" + if (environment != "live") { + baseUrl = "https://api-m.sandbox.paypal.com" + } else { + baseUrl = "https://api-m.paypal.com" + } + + const base64Key = Buffer.from(`${clientId}:${clientSecret}`).toString('base64'); + + let options: OptionsWithUri = { + headers: { + 'Authorization': `Basic ${base64Key}`, + }, + method: 'POST', + uri: `${baseUrl}/v1/oauth2/token`, + form: { + grant_type: "client_credentials" + } + } + + try { + await this.helpers.request!(options); + return { + status: 'OK', + message: 'Authentication successful!', + }; + } + catch (error) { + return { + status: 'Error', + message: `Connection details not valid: ${error.message}` + }; + } + } + } + } } diff --git a/packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js b/packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js new file mode 100644 index 0000000000000..a0dad46dbc839 --- /dev/null +++ b/packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js @@ -0,0 +1,93 @@ +const PayPalNodeModule = require('../../../nodes/PayPal/PayPal.node.ts') + +describe('testCredentials', () => { + let node = new PayPalNodeModule.PayPal() + const mockSuccessfulResponse = {"access_token": "ABC"} + const expectedSandboxUri = "https://api-m.sandbox.paypal.com/v1/oauth2/token" + const expectedLiveUri = "https://api-m.paypal.com/v1/oauth2/token" + let called = [] + + + let mockCredentials = { + id: 1, + name: "test", + type: "payPalApi", + nodesAccess: [], + data: { + "clientId": "mockId", + "secret": "mockSecret", + "env": "sanbox" + } + } + + it('Method exists', async () => { + + expect(node.methods.credentialTest.payPalApiTest).toBeTruthy() + + }) + + function patchHelper(node, response, error) { + called = [] + function mockRequest(options) { + console.log(options) + called.push(options) + if (error) { + throw new Error("Mocked error") + } + return mockSuccessfulResponse + } + node.methods.credentialTest.helpers = {request: mockRequest} + } + + it('Calls Mocked API Sandbox Environment', async () => { + + patchHelper(node, mockSuccessfulResponse) + + result = await node.methods.credentialTest.payPalApiTest(mockCredentials) + + expect(result).toEqual({ + status: 'OK', + message: 'Authentication successful!', + }) + expect(called[0].uri).toEqual(expectedSandboxUri) + }) + + it('Calls Mocked API Live Environment', async () => { + + patchHelper(node, mockSuccessfulResponse) + + mockCredentials.data.env = "live" + result = await node.methods.credentialTest.payPalApiTest(mockCredentials) + + expect(result).toEqual({ + status: 'OK', + message: 'Authentication successful!', + }) + expect(called[0].uri).toEqual(expectedLiveUri) + }) + + it('Calls Mocked API Raises Error', async () => { + + patchHelper(node, {}, true) + + result = await node.methods.credentialTest.payPalApiTest(mockCredentials) + + expect(result).toEqual({ + status: 'Error', + message: 'Connection details not valid: Mocked error', + }) + }) + + it('Calls Mocked Invalid Input', async () => { + + mockCredentials.data.secret = undefined + + result = await node.methods.credentialTest.payPalApiTest(mockCredentials) + + expect(result).toEqual({ + status: 'Error', + message: 'Connection details not valid: missing credentials', + }) + }) +}) + From bf87cf90371b29759f7945a44c43163c0a078797 Mon Sep 17 00:00:00 2001 From: paolo-rechia Date: Thu, 31 Mar 2022 11:47:11 +0200 Subject: [PATCH 2/5] Deletes unit tests --- .../PayPal.node.testCredentials.test.js | 93 ------------------- 1 file changed, 93 deletions(-) delete mode 100644 packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js diff --git a/packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js b/packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js deleted file mode 100644 index a0dad46dbc839..0000000000000 --- a/packages/nodes-base/test/nodes/PayPal/PayPal.node.testCredentials.test.js +++ /dev/null @@ -1,93 +0,0 @@ -const PayPalNodeModule = require('../../../nodes/PayPal/PayPal.node.ts') - -describe('testCredentials', () => { - let node = new PayPalNodeModule.PayPal() - const mockSuccessfulResponse = {"access_token": "ABC"} - const expectedSandboxUri = "https://api-m.sandbox.paypal.com/v1/oauth2/token" - const expectedLiveUri = "https://api-m.paypal.com/v1/oauth2/token" - let called = [] - - - let mockCredentials = { - id: 1, - name: "test", - type: "payPalApi", - nodesAccess: [], - data: { - "clientId": "mockId", - "secret": "mockSecret", - "env": "sanbox" - } - } - - it('Method exists', async () => { - - expect(node.methods.credentialTest.payPalApiTest).toBeTruthy() - - }) - - function patchHelper(node, response, error) { - called = [] - function mockRequest(options) { - console.log(options) - called.push(options) - if (error) { - throw new Error("Mocked error") - } - return mockSuccessfulResponse - } - node.methods.credentialTest.helpers = {request: mockRequest} - } - - it('Calls Mocked API Sandbox Environment', async () => { - - patchHelper(node, mockSuccessfulResponse) - - result = await node.methods.credentialTest.payPalApiTest(mockCredentials) - - expect(result).toEqual({ - status: 'OK', - message: 'Authentication successful!', - }) - expect(called[0].uri).toEqual(expectedSandboxUri) - }) - - it('Calls Mocked API Live Environment', async () => { - - patchHelper(node, mockSuccessfulResponse) - - mockCredentials.data.env = "live" - result = await node.methods.credentialTest.payPalApiTest(mockCredentials) - - expect(result).toEqual({ - status: 'OK', - message: 'Authentication successful!', - }) - expect(called[0].uri).toEqual(expectedLiveUri) - }) - - it('Calls Mocked API Raises Error', async () => { - - patchHelper(node, {}, true) - - result = await node.methods.credentialTest.payPalApiTest(mockCredentials) - - expect(result).toEqual({ - status: 'Error', - message: 'Connection details not valid: Mocked error', - }) - }) - - it('Calls Mocked Invalid Input', async () => { - - mockCredentials.data.secret = undefined - - result = await node.methods.credentialTest.payPalApiTest(mockCredentials) - - expect(result).toEqual({ - status: 'Error', - message: 'Connection details not valid: missing credentials', - }) - }) -}) - From b0aa106e9008151fea0e150c5801a10b250e8ee2 Mon Sep 17 00:00:00 2001 From: Jonathan Bennetts Date: Thu, 31 Mar 2022 17:44:16 +0100 Subject: [PATCH 3/5] :rotating_light: Fixed lint issues --- .../nodes-base/nodes/PayPal/PayPal.node.ts | 102 +++++++++--------- 1 file changed, 51 insertions(+), 51 deletions(-) diff --git a/packages/nodes-base/nodes/PayPal/PayPal.node.ts b/packages/nodes-base/nodes/PayPal/PayPal.node.ts index ac1adf8758e6d..dee8dd44580fb 100644 --- a/packages/nodes-base/nodes/PayPal/PayPal.node.ts +++ b/packages/nodes-base/nodes/PayPal/PayPal.node.ts @@ -1,14 +1,14 @@ import { - OptionsWithUri + OptionsWithUri } from 'request'; import { IExecuteFunctions, } from 'n8n-core'; import { + ICredentialsDecrypted, + ICredentialTestFunctions, IDataObject, - ICredentialTestFunctions, - ICredentialsDecrypted, - INodeCredentialTestResult, + INodeCredentialTestResult, INodeExecutionData, INodeType, INodeTypeDescription, @@ -52,7 +52,7 @@ export class PayPal implements INodeType { { name: 'payPalApi', required: true, - testedBy: 'payPalApiTest' + testedBy: 'payPalApiTest', }, ], properties: [ @@ -177,55 +177,55 @@ export class PayPal implements INodeType { return [this.helpers.returnJsonArray(returnData)]; } - methods = { - credentialTest: { - async payPalApiTest(this: ICredentialTestFunctions, credential: ICredentialsDecrypted): Promise { - const credentials = credential.data; - const clientId = credentials!.clientId - const clientSecret = credentials!.secret - const environment = credentials!.env + methods = { + credentialTest: { + async payPalApiTest(this: ICredentialTestFunctions, credential: ICredentialsDecrypted): Promise { + const credentials = credential.data; + const clientId = credentials!.clientId; + const clientSecret = credentials!.secret; + const environment = credentials!.env; - if (!clientId || !clientSecret || !environment) { - return { - status: 'Error', - message: `Connection details not valid: missing credentials` - }; - } + if (!clientId || !clientSecret || !environment) { + return { + status: 'Error', + message: `Connection details not valid: missing credentials`, + }; + } - let baseUrl = "" - if (environment != "live") { - baseUrl = "https://api-m.sandbox.paypal.com" - } else { - baseUrl = "https://api-m.paypal.com" - } + let baseUrl = ''; + if (environment !== 'live') { + baseUrl = 'https://api-m.sandbox.paypal.com'; + } else { + baseUrl = 'https://api-m.paypal.com'; + } - const base64Key = Buffer.from(`${clientId}:${clientSecret}`).toString('base64'); + const base64Key = Buffer.from(`${clientId}:${clientSecret}`).toString('base64'); - let options: OptionsWithUri = { - headers: { - 'Authorization': `Basic ${base64Key}`, - }, - method: 'POST', - uri: `${baseUrl}/v1/oauth2/token`, - form: { - grant_type: "client_credentials" - } - } + const options: OptionsWithUri = { + headers: { + 'Authorization': `Basic ${base64Key}`, + }, + method: 'POST', + uri: `${baseUrl}/v1/oauth2/token`, + form: { + grant_type: 'client_credentials', + }, + }; - try { - await this.helpers.request!(options); - return { - status: 'OK', - message: 'Authentication successful!', - }; - } - catch (error) { - return { - status: 'Error', - message: `Connection details not valid: ${error.message}` - }; - } - } - } - } + try { + await this.helpers.request!(options); + return { + status: 'OK', + message: 'Authentication successful!', + }; + } + catch (error) { + return { + status: 'Error', + message: `Connection details not valid: ${error.message}`, + }; + } + }, + }, + }; } From 2c75bd093701cd17e217fb5d706b7938563f7ef8 Mon Sep 17 00:00:00 2001 From: Jonathan Bennetts Date: Mon, 4 Apr 2022 10:58:19 +0100 Subject: [PATCH 4/5] Added changes from PR#2568 --- packages/nodes-base/credentials/PayPalApi.credentials.ts | 2 +- packages/nodes-base/nodes/PayPal/GenericFunctions.ts | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/nodes-base/credentials/PayPalApi.credentials.ts b/packages/nodes-base/credentials/PayPalApi.credentials.ts index 897a66b627e98..9b2514efffe28 100644 --- a/packages/nodes-base/credentials/PayPalApi.credentials.ts +++ b/packages/nodes-base/credentials/PayPalApi.credentials.ts @@ -28,7 +28,7 @@ export class PayPalApi implements ICredentialType { default: 'live', options: [ { - name: 'Sanbox', + name: 'Sandbox', value: 'sanbox', }, { diff --git a/packages/nodes-base/nodes/PayPal/GenericFunctions.ts b/packages/nodes-base/nodes/PayPal/GenericFunctions.ts index a7859b335c8ec..1e8b84b4ebb3b 100644 --- a/packages/nodes-base/nodes/PayPal/GenericFunctions.ts +++ b/packages/nodes-base/nodes/PayPal/GenericFunctions.ts @@ -38,8 +38,8 @@ export async function payPalApiRequest(this: IHookFunctions | IExecuteFunctions function getEnvironment(env: string): string { // @ts-ignore return { - 'sanbox': 'https://api.sandbox.paypal.com', - 'live': 'https://api.paypal.com', + 'sanbox': 'https://api-m.sandbox.paypal.com', + 'live': 'https://api-m.paypal.com', }[env]; } From 7c3eebf6ebd48326feb96c8ca2d4d6fce12bd565 Mon Sep 17 00:00:00 2001 From: Jonathan Bennetts Date: Mon, 4 Apr 2022 11:08:38 +0100 Subject: [PATCH 5/5] Moved methods to above execute --- .../nodes-base/nodes/PayPal/PayPal.node.ts | 103 +++++++++--------- 1 file changed, 52 insertions(+), 51 deletions(-) diff --git a/packages/nodes-base/nodes/PayPal/PayPal.node.ts b/packages/nodes-base/nodes/PayPal/PayPal.node.ts index dee8dd44580fb..36e4d6ee3499a 100644 --- a/packages/nodes-base/nodes/PayPal/PayPal.node.ts +++ b/packages/nodes-base/nodes/PayPal/PayPal.node.ts @@ -82,6 +82,58 @@ export class PayPal implements INodeType { ], }; + methods = { + credentialTest: { + async payPalApiTest(this: ICredentialTestFunctions, credential: ICredentialsDecrypted): Promise { + const credentials = credential.data; + const clientId = credentials!.clientId; + const clientSecret = credentials!.secret; + const environment = credentials!.env; + + if (!clientId || !clientSecret || !environment) { + return { + status: 'Error', + message: `Connection details not valid: missing credentials`, + }; + } + + let baseUrl = ''; + if (environment !== 'live') { + baseUrl = 'https://api-m.sandbox.paypal.com'; + } else { + baseUrl = 'https://api-m.paypal.com'; + } + + const base64Key = Buffer.from(`${clientId}:${clientSecret}`).toString('base64'); + + const options: OptionsWithUri = { + headers: { + 'Authorization': `Basic ${base64Key}`, + }, + method: 'POST', + uri: `${baseUrl}/v1/oauth2/token`, + form: { + grant_type: 'client_credentials', + }, + }; + + try { + await this.helpers.request!(options); + return { + status: 'OK', + message: 'Authentication successful!', + }; + } + catch (error) { + return { + status: 'Error', + message: `Connection details not valid: ${error.message}`, + }; + } + }, + }, + }; + async execute(this: IExecuteFunctions): Promise { const items = this.getInputData(); const returnData: IDataObject[] = []; @@ -177,55 +229,4 @@ export class PayPal implements INodeType { return [this.helpers.returnJsonArray(returnData)]; } - methods = { - credentialTest: { - async payPalApiTest(this: ICredentialTestFunctions, credential: ICredentialsDecrypted): Promise { - const credentials = credential.data; - const clientId = credentials!.clientId; - const clientSecret = credentials!.secret; - const environment = credentials!.env; - - if (!clientId || !clientSecret || !environment) { - return { - status: 'Error', - message: `Connection details not valid: missing credentials`, - }; - } - - let baseUrl = ''; - if (environment !== 'live') { - baseUrl = 'https://api-m.sandbox.paypal.com'; - } else { - baseUrl = 'https://api-m.paypal.com'; - } - - const base64Key = Buffer.from(`${clientId}:${clientSecret}`).toString('base64'); - - const options: OptionsWithUri = { - headers: { - 'Authorization': `Basic ${base64Key}`, - }, - method: 'POST', - uri: `${baseUrl}/v1/oauth2/token`, - form: { - grant_type: 'client_credentials', - }, - }; - - try { - await this.helpers.request!(options); - return { - status: 'OK', - message: 'Authentication successful!', - }; - } - catch (error) { - return { - status: 'Error', - message: `Connection details not valid: ${error.message}`, - }; - } - }, - }, - }; }