mirror of
https://github.com/n8n-io/n8n.git
synced 2024-11-14 00:24:07 -08:00
31d8f478ee
Also, 1. Consistent CORS support ~on all three webhook types~ waiting webhooks never supported CORS. I'll fix that in another PR 2. [Fixes binary-data handling when request body is text, json, or xml](https://linear.app/n8n/issue/NODE-505/webhook-binary-data-handling-fails-for-textplain-files). 3. Reduced number of middleware that each request has to go through. 4. Removed the need to maintain webhook endpoints in the auth-exception list. 5. Skip all middlewares (apart from `compression`) on Webhook routes. 6. move `multipart/form-data` support out of individual nodes 7. upgrade `formidable` 8. fix the filenames on binary-data in webhooks nodes 9. add unit tests and integration tests for webhook request handling, and increase test coverage
77 lines
2.6 KiB
TypeScript
77 lines
2.6 KiB
TypeScript
import type { SuperAgentTest } from 'supertest';
|
|
import { agent as testAgent } from 'supertest';
|
|
import { mock } from 'jest-mock-extended';
|
|
|
|
import config from '@/config';
|
|
import { AbstractServer } from '@/AbstractServer';
|
|
import { ActiveWorkflowRunner } from '@/ActiveWorkflowRunner';
|
|
import { ExternalHooks } from '@/ExternalHooks';
|
|
import { InternalHooks } from '@/InternalHooks';
|
|
import { TestWebhooks } from '@/TestWebhooks';
|
|
import { WaitingWebhooks } from '@/WaitingWebhooks';
|
|
import type { IResponseCallbackData } from '@/Interfaces';
|
|
|
|
import { mockInstance } from '../integration/shared/utils';
|
|
|
|
let agent: SuperAgentTest;
|
|
|
|
describe('WebhookServer', () => {
|
|
mockInstance(ExternalHooks);
|
|
mockInstance(InternalHooks);
|
|
|
|
describe('CORS', () => {
|
|
const corsOrigin = 'https://example.com';
|
|
const activeWorkflowRunner = mockInstance(ActiveWorkflowRunner);
|
|
const testWebhooks = mockInstance(TestWebhooks);
|
|
mockInstance(WaitingWebhooks);
|
|
|
|
beforeAll(async () => {
|
|
const server = new (class extends AbstractServer {
|
|
testWebhooksEnabled = true;
|
|
})();
|
|
await server.start();
|
|
agent = testAgent(server.app);
|
|
});
|
|
|
|
const tests = [
|
|
['webhook', activeWorkflowRunner],
|
|
['webhookTest', testWebhooks],
|
|
// TODO: enable webhookWaiting after CORS support is added
|
|
// ['webhookWaiting', waitingWebhooks],
|
|
] as const;
|
|
|
|
for (const [key, manager] of tests) {
|
|
describe(`for ${key}`, () => {
|
|
it('should handle preflight requests', async () => {
|
|
const pathPrefix = config.getEnv(`endpoints.${key}`);
|
|
manager.getWebhookMethods.mockResolvedValueOnce(['GET']);
|
|
|
|
const response = await agent.options(`/${pathPrefix}/abcd`).set('origin', corsOrigin);
|
|
expect(response.statusCode).toEqual(204);
|
|
expect(response.body).toEqual({});
|
|
expect(response.headers['access-control-allow-origin']).toEqual(corsOrigin);
|
|
expect(response.headers['access-control-allow-methods']).toEqual('OPTIONS, GET');
|
|
});
|
|
|
|
it('should handle regular requests', async () => {
|
|
const pathPrefix = config.getEnv(`endpoints.${key}`);
|
|
manager.getWebhookMethods.mockResolvedValueOnce(['GET']);
|
|
manager.executeWebhook.mockResolvedValueOnce(mockResponse({ test: true }));
|
|
|
|
const response = await agent.get(`/${pathPrefix}/abcd`).set('origin', corsOrigin);
|
|
expect(response.statusCode).toEqual(200);
|
|
expect(response.body).toEqual({ test: true });
|
|
expect(response.headers['access-control-allow-origin']).toEqual(corsOrigin);
|
|
});
|
|
});
|
|
}
|
|
|
|
const mockResponse = (data = {}, status = 200) => {
|
|
const response = mock<IResponseCallbackData>();
|
|
response.responseCode = status;
|
|
response.data = data;
|
|
return response;
|
|
};
|
|
});
|
|
});
|