fix(core): Improve axios error handling in nodes (#5699)

* fix(core): Improve axios error handling in nodes

* handle axios errors without a response (like when connection fails)

---------

Co-authored-by: कारतोफ्फेलस्क्रिप्ट™ <aditya@netroy.in>
This commit is contained in:
agobrech 2023-03-20 17:34:14 +01:00 committed by GitHub
parent 46d013cbc5
commit 33d9784319
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 40 additions and 36 deletions

View file

@ -39,6 +39,7 @@
"@types/crypto-js": "^4.0.1", "@types/crypto-js": "^4.0.1",
"@types/express": "^4.17.6", "@types/express": "^4.17.6",
"@types/lodash.get": "^4.4.6", "@types/lodash.get": "^4.4.6",
"@types/lodash.pick": "^4.4.7",
"@types/mime-types": "^2.1.0", "@types/mime-types": "^2.1.0",
"@types/request-promise-native": "~1.0.15", "@types/request-promise-native": "~1.0.15",
"@types/uuid": "^8.3.2" "@types/uuid": "^8.3.2"
@ -54,6 +55,7 @@
"flatted": "^3.2.4", "flatted": "^3.2.4",
"form-data": "^4.0.0", "form-data": "^4.0.0",
"lodash.get": "^4.4.2", "lodash.get": "^4.4.2",
"lodash.pick": "^4.4.0",
"mime-types": "^2.1.27", "mime-types": "^2.1.27",
"n8n-workflow": "workspace:*", "n8n-workflow": "workspace:*",
"oauth-1.0a": "^2.2.6", "oauth-1.0a": "^2.2.6",

View file

@ -73,6 +73,7 @@ import {
ExpressionError, ExpressionError,
} from 'n8n-workflow'; } from 'n8n-workflow';
import pick from 'lodash.pick';
import { Agent } from 'https'; import { Agent } from 'https';
import { stringify } from 'qs'; import { stringify } from 'qs';
import type { Token } from 'oauth-1.0a'; import type { Token } from 'oauth-1.0a';
@ -667,50 +668,47 @@ async function proxyRequestToAxios(
return body; return body;
} }
} catch (error) { } catch (error) {
const { request, response, isAxiosError, toJSON, config, ...errorData } = error; const { config, response } = error;
if (configObject.simple === false && response) {
if (configObject.resolveWithFullResponse) {
return {
body: response.data,
headers: response.headers,
statusCode: response.status,
statusMessage: response.statusText,
};
} else {
return response.data;
}
}
// Axios hydrates the original error with more data. We extract them. // Axios hydrates the original error with more data. We extract them.
// https://github.com/axios/axios/blob/master/lib/core/enhanceError.js // https://github.com/axios/axios/blob/master/lib/core/enhanceError.js
// Note: `code` is ignored as it's an expected part of the errorData. // Note: `code` is ignored as it's an expected part of the errorData.
if (response) { if (error.isAxiosError) {
Logger.debug('Request proxied to Axios failed', { status: response.status }); if (response) {
let responseData = response.data; Logger.debug('Request proxied to Axios failed', { status: response.status });
let responseData = response.data;
if (Buffer.isBuffer(responseData) || responseData instanceof Readable) { if (Buffer.isBuffer(responseData) || responseData instanceof Readable) {
responseData = await binaryToBuffer(responseData).then((buffer) => responseData = await binaryToBuffer(responseData).then((buffer) =>
buffer.toString('utf-8'), buffer.toString('utf-8'),
); );
}
if (configObject.simple === false) {
if (configObject.resolveWithFullResponse) {
return {
body: responseData,
headers: response.headers,
statusCode: response.status,
statusMessage: response.statusText,
};
} else {
return responseData;
}
}
const message = `${response.status as number} - ${JSON.stringify(responseData)}`;
throw Object.assign(new Error(message, { cause: error }), {
status: response.status,
options: pick(config ?? {}, ['url', 'method', 'data', 'headers']),
});
} else {
throw Object.assign(new Error(error.message, { cause: error }), {
options: pick(config ?? {}, ['url', 'method', 'data', 'headers']),
});
} }
error.message = `${response.status as number} - ${JSON.stringify(responseData)}`;
} }
error.cause = errorData;
error.error = error.response?.data || errorData;
error.statusCode = error.response?.status;
error.options = config || {};
// Remove not needed data and so also remove circular references
error.request = undefined;
error.config = undefined;
error.options.adapter = undefined;
error.options.httpsAgent = undefined;
error.options.paramsSerializer = undefined;
error.options.transformRequest = undefined;
error.options.transformResponse = undefined;
error.options.validateStatus = undefined;
throw error; throw error;
} }
} }

View file

@ -404,6 +404,7 @@ importers:
'@types/crypto-js': ^4.0.1 '@types/crypto-js': ^4.0.1
'@types/express': ^4.17.6 '@types/express': ^4.17.6
'@types/lodash.get': ^4.4.6 '@types/lodash.get': ^4.4.6
'@types/lodash.pick': ^4.4.7
'@types/mime-types': ^2.1.0 '@types/mime-types': ^2.1.0
'@types/request-promise-native': ~1.0.15 '@types/request-promise-native': ~1.0.15
'@types/uuid': ^8.3.2 '@types/uuid': ^8.3.2
@ -417,6 +418,7 @@ importers:
flatted: ^3.2.4 flatted: ^3.2.4
form-data: ^4.0.0 form-data: ^4.0.0
lodash.get: ^4.4.2 lodash.get: ^4.4.2
lodash.pick: ^4.4.0
mime-types: ^2.1.27 mime-types: ^2.1.27
n8n-workflow: workspace:* n8n-workflow: workspace:*
oauth-1.0a: ^2.2.6 oauth-1.0a: ^2.2.6
@ -437,6 +439,7 @@ importers:
flatted: 3.2.7 flatted: 3.2.7
form-data: 4.0.0 form-data: 4.0.0
lodash.get: 4.4.2 lodash.get: 4.4.2
lodash.pick: 4.4.0
mime-types: 2.1.35 mime-types: 2.1.35
n8n-workflow: link:../workflow n8n-workflow: link:../workflow
oauth-1.0a: 2.2.6 oauth-1.0a: 2.2.6
@ -452,6 +455,7 @@ importers:
'@types/crypto-js': 4.1.1 '@types/crypto-js': 4.1.1
'@types/express': 4.17.14 '@types/express': 4.17.14
'@types/lodash.get': 4.4.7 '@types/lodash.get': 4.4.7
'@types/lodash.pick': 4.4.7
'@types/mime-types': 2.1.1 '@types/mime-types': 2.1.1
'@types/request-promise-native': 1.0.18 '@types/request-promise-native': 1.0.18
'@types/uuid': 8.3.4 '@types/uuid': 8.3.4