update webhook response (#2006)

* add hint to 'webhook not registered' error

* Convert hints to constants
This commit is contained in:
MedAliMarz 2021-07-23 20:56:18 +02:00 committed by GitHub
parent 34c1123636
commit 2a99a77b43
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 21 additions and 8 deletions

View file

@ -39,6 +39,8 @@ import {
LoggerProxy as Logger, LoggerProxy as Logger,
} from 'n8n-workflow'; } from 'n8n-workflow';
const WEBHOOK_PROD_UNREGISTERED_HINT = `The workflow must be active for a production URL to run successfully. You can activate the workflow using the toggle in the top-right of the editor. Note that unlike test URL calls, production URL calls aren't shown on the canvas (only in the executions list)`;
export class ActiveWorkflowRunner { export class ActiveWorkflowRunner {
private activeWorkflows: ActiveWorkflows | null = null; private activeWorkflows: ActiveWorkflows | null = null;
@ -148,7 +150,7 @@ export class ActiveWorkflowRunner {
const dynamicWebhooks = await Db.collections.Webhook?.find({ webhookId, method: httpMethod, pathLength: pathElements.length }); const dynamicWebhooks = await Db.collections.Webhook?.find({ webhookId, method: httpMethod, pathLength: pathElements.length });
if (dynamicWebhooks === undefined || dynamicWebhooks.length === 0) { if (dynamicWebhooks === undefined || dynamicWebhooks.length === 0) {
// The requested webhook is not registered // The requested webhook is not registered
throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404); throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404, WEBHOOK_PROD_UNREGISTERED_HINT);
} }
let maxMatches = 0; let maxMatches = 0;
@ -169,7 +171,7 @@ export class ActiveWorkflowRunner {
} }
}); });
if (webhook === undefined) { if (webhook === undefined) {
throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404); throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404, WEBHOOK_PROD_UNREGISTERED_HINT);
} }
path = webhook!.webhookPath; path = webhook!.webhookPath;

View file

@ -21,17 +21,21 @@ export class ResponseError extends Error {
// The HTTP status code of response // The HTTP status code of response
httpStatusCode?: number; httpStatusCode?: number;
// The error code in the resonse // The error code in the response
errorCode?: number; errorCode?: number;
// The error hint the response
hint?: string;
/** /**
* Creates an instance of ResponseError. * Creates an instance of ResponseError.
* @param {string} message The error message * @param {string} message The error message
* @param {number} [errorCode] The error code which can be used by frontend to identify the actual error * @param {number} [errorCode] The error code which can be used by frontend to identify the actual error
* @param {number} [httpStatusCode] The HTTP status code the response should have * @param {number} [httpStatusCode] The HTTP status code the response should have
* @param {string} [hint] The error hint to provide a context (webhook related)
* @memberof ResponseError * @memberof ResponseError
*/ */
constructor(message: string, errorCode?: number, httpStatusCode?: number) { constructor(message: string, errorCode?: number, httpStatusCode?: number, hint?:string) {
super(message); super(message);
this.name = 'ResponseError'; this.name = 'ResponseError';
@ -41,6 +45,9 @@ export class ResponseError extends Error {
if (httpStatusCode) { if (httpStatusCode) {
this.httpStatusCode = httpStatusCode; this.httpStatusCode = httpStatusCode;
} }
if (hint) {
this.hint = hint;
}
} }
} }
@ -91,6 +98,7 @@ export function sendErrorResponse(res: Response, error: ResponseError) {
const response = { const response = {
code: 0, code: 0,
message: 'Unknown error', message: 'Unknown error',
hint: '',
}; };
if (error.name === 'NodeApiError') { if (error.name === 'NodeApiError') {
@ -103,6 +111,9 @@ export function sendErrorResponse(res: Response, error: ResponseError) {
if (error.message) { if (error.message) {
response.message = error.message; response.message = error.message;
} }
if (error.hint) {
response.hint = error.hint;
}
if (error.stack && process.env.NODE_ENV !== 'production') { if (error.stack && process.env.NODE_ENV !== 'production') {
// @ts-ignore // @ts-ignore
response.stack = error.stack; response.stack = error.stack;

View file

@ -21,7 +21,7 @@ import {
WorkflowExecuteMode, WorkflowExecuteMode,
} from 'n8n-workflow'; } from 'n8n-workflow';
const WEBHOOK_TEST_UNREGISTERED_HINT = `Click the 'Execute workflow' button on the canvas, then try again. (In test mode, the webhook only works for one call after you click this button)`;
export class TestWebhooks { export class TestWebhooks {
@ -72,7 +72,7 @@ export class TestWebhooks {
webhookData = this.activeWebhooks!.get(httpMethod, pathElements.join('/'), webhookId); webhookData = this.activeWebhooks!.get(httpMethod, pathElements.join('/'), webhookId);
if (webhookData === undefined) { if (webhookData === undefined) {
// The requested webhook is not registered // The requested webhook is not registered
throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404); throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404, WEBHOOK_TEST_UNREGISTERED_HINT);
} }
path = webhookData.path; path = webhookData.path;
@ -90,7 +90,7 @@ export class TestWebhooks {
// TODO: Clean that duplication up one day and improve code generally // TODO: Clean that duplication up one day and improve code generally
if (this.testWebhookData[webhookKey] === undefined) { if (this.testWebhookData[webhookKey] === undefined) {
// The requested webhook is not registered // The requested webhook is not registered
throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404); throw new ResponseHelper.ResponseError(`The requested webhook "${httpMethod} ${path}" is not registered.`, 404, 404, WEBHOOK_TEST_UNREGISTERED_HINT);
} }
const workflow = this.testWebhookData[webhookKey].workflow; const workflow = this.testWebhookData[webhookKey].workflow;
@ -145,7 +145,7 @@ export class TestWebhooks {
if (webhookMethods === undefined) { if (webhookMethods === undefined) {
// The requested webhook is not registered // The requested webhook is not registered
throw new ResponseHelper.ResponseError(`The requested webhook "${path}" is not registered.`, 404, 404); throw new ResponseHelper.ResponseError(`The requested webhook "${path}" is not registered.`, 404, 404, WEBHOOK_TEST_UNREGISTERED_HINT);
} }
return webhookMethods; return webhookMethods;