From 4ca6e8767afd959acdcf439747b992626059e4f3 Mon Sep 17 00:00:00 2001 From: Konstantin Vyatkin Date: Wed, 27 May 2020 09:07:00 -0400 Subject: [PATCH 1/2] remove code duplication in custom errors --- src/body.js | 2 +- src/errors/abort-error.js | 27 +++++---------------------- src/errors/base.js | 20 ++++++++++++++++++++ src/errors/fetch-error.js | 36 ++++++++++++++---------------------- src/index.js | 4 ++-- test/main.js | 2 +- 6 files changed, 43 insertions(+), 48 deletions(-) create mode 100644 src/errors/base.js diff --git a/src/body.js b/src/body.js index ad1c0402a..0000e7aa4 100644 --- a/src/body.js +++ b/src/body.js @@ -9,7 +9,7 @@ import Stream, {PassThrough} from 'stream'; import {types} from 'util'; import Blob from 'fetch-blob'; -import FetchError from './errors/fetch-error.js'; +import {FetchError} from './errors/fetch-error.js'; import {isBlob, isURLSearchParameters, isAbortError} from './utils/is.js'; const INTERNALS = Symbol('Body internals'); diff --git a/src/errors/abort-error.js b/src/errors/abort-error.js index 27c7545ff..0b62f1cd3 100644 --- a/src/errors/abort-error.js +++ b/src/errors/abort-error.js @@ -1,27 +1,10 @@ -/** - * Abort-error.js - * - * AbortError interface for cancelled requests - */ +import {FetchBaseError} from './base.js'; /** - * Create AbortError instance - * - * @param String message Error message for human - * @param String type Error type for machine - * @param String systemError For Node.js system error - * @return AbortError + * AbortError interface for cancelled requests */ -export default class AbortError extends Error { - constructor(message) { - super(message); - - this.type = 'aborted'; - this.message = message; - this.name = 'AbortError'; - this[Symbol.toStringTag] = 'AbortError'; - - // Hide custom error implementation details from end-users - Error.captureStackTrace(this, this.constructor); +export class AbortError extends FetchBaseError { + constructor(message, type = 'aborted') { + super(message, type); } } diff --git a/src/errors/base.js b/src/errors/base.js new file mode 100644 index 000000000..95fb1b253 --- /dev/null +++ b/src/errors/base.js @@ -0,0 +1,20 @@ +'use strict'; + +export class FetchBaseError extends Error { + constructor(message, type) { + super(message); + // Hide custom error implementation details from end-users + Error.captureStackTrace(this, this.constructor); + + this.type = type; + } + + get name() { + return this.constructor.name; + } + + get [Symbol.toStringTag]() { + return this.constructor.name; + } +} + diff --git a/src/errors/fetch-error.js b/src/errors/fetch-error.js index 87b696a7b..ac5a4dcff 100644 --- a/src/errors/fetch-error.js +++ b/src/errors/fetch-error.js @@ -1,34 +1,26 @@ + +import {FetchBaseError} from './base.js'; + /** - * Fetch-error.js - * - * FetchError interface for operational errors - */ + * @typedef {{ address?: string, code: string, dest?: string, errno: number, info?: object, message: string, path?: string, port?: number, syscall: string}} SystemError +*/ /** - * Create FetchError instance - * - * @param String message Error message for human - * @param String type Error type for machine - * @param Object systemError For Node.js system error - * @return FetchError + * FetchError interface for operational errors */ -export default class FetchError extends Error { +export class FetchError extends FetchBaseError { + /** + * @param {string} message - Error message for human + * @param {string} type - Error type for machine + * @param {SystemError} [systemError] - For Node.js system error + */ constructor(message, type, systemError) { - super(message); - - this.message = message; - this.type = type; - this.name = 'FetchError'; - this[Symbol.toStringTag] = 'FetchError'; - + super(message, type); // When err.type is `system`, err.erroredSysCall contains system error and err.code contains system error code if (systemError) { // eslint-disable-next-line no-multi-assign this.code = this.errno = systemError.code; - this.erroredSysCall = systemError; + this.erroredSysCall = systemError.syscall; } - - // Hide custom error implementation details from end-users - Error.captureStackTrace(this, this.constructor); } } diff --git a/src/index.js b/src/index.js index 95f428312..3eee3e3ad 100644 --- a/src/index.js +++ b/src/index.js @@ -16,8 +16,8 @@ import {writeToStream, getTotalBytes} from './body.js'; import Response from './response.js'; import Headers, {fromRawHeaders} from './headers.js'; import Request, {getNodeRequestOptions} from './request.js'; -import FetchError from './errors/fetch-error.js'; -import AbortError from './errors/abort-error.js'; +import {FetchError} from './errors/fetch-error.js'; +import {AbortError} from './errors/abort-error.js'; import {isRedirect} from './utils/is-redirect.js'; export {Headers, Request, Response, FetchError, AbortError, isRedirect}; diff --git a/test/main.js b/test/main.js index b1500b89b..2961ec3db 100644 --- a/test/main.js +++ b/test/main.js @@ -28,7 +28,7 @@ import fetch, { Request, Response } from '../src/index.js'; -import FetchErrorOrig from '../src/errors/fetch-error.js'; +import {FetchError as FetchErrorOrig} from '../src/errors/fetch-error.js'; import HeadersOrig, {fromRawHeaders} from '../src/headers.js'; import RequestOrig from '../src/request.js'; import ResponseOrig from '../src/response.js'; From 6848a55f8395685adb7f15ec13323aadc492bd55 Mon Sep 17 00:00:00 2001 From: Konstantin Vyatkin Date: Thu, 28 May 2020 23:40:08 -0400 Subject: [PATCH 2/2] check using base class --- src/body.js | 7 ++++--- src/errors/fetch-error.js | 2 +- src/utils/is.js | 9 --------- 3 files changed, 5 insertions(+), 13 deletions(-) diff --git a/src/body.js b/src/body.js index 0000e7aa4..0e8534d56 100644 --- a/src/body.js +++ b/src/body.js @@ -10,7 +10,8 @@ import {types} from 'util'; import Blob from 'fetch-blob'; import {FetchError} from './errors/fetch-error.js'; -import {isBlob, isURLSearchParameters, isAbortError} from './utils/is.js'; +import {FetchBaseError} from './errors/base.js'; +import {isBlob, isURLSearchParameters} from './utils/is.js'; const INTERNALS = Symbol('Body internals'); @@ -60,7 +61,7 @@ export default class Body { if (body instanceof Stream) { body.on('error', err => { - const error = isAbortError(err) ? + const error = err instanceof FetchBaseError ? err : new FetchError(`Invalid response body while trying to fetch ${this.url}: ${err.message}`, 'system', err); this[INTERNALS].error = error; @@ -198,7 +199,7 @@ async function consumeBody(data) { accum.push(chunk); } } catch (error) { - if (isAbortError(error) || error instanceof FetchError) { + if (error instanceof FetchBaseError) { throw error; } else { // Other errors, such as incorrect content-encoding diff --git a/src/errors/fetch-error.js b/src/errors/fetch-error.js index ac5a4dcff..f7ae5cc4a 100644 --- a/src/errors/fetch-error.js +++ b/src/errors/fetch-error.js @@ -11,7 +11,7 @@ import {FetchBaseError} from './base.js'; export class FetchError extends FetchBaseError { /** * @param {string} message - Error message for human - * @param {string} type - Error type for machine + * @param {string} [type] - Error type for machine * @param {SystemError} [systemError] - For Node.js system error */ constructor(message, type, systemError) { diff --git a/src/utils/is.js b/src/utils/is.js index b3bbbf499..ea74a0021 100644 --- a/src/utils/is.js +++ b/src/utils/is.js @@ -57,12 +57,3 @@ export const isAbortSignal = object => { ); }; -/** - * Check if `obj` is an instance of AbortError. - * - * @param {*} obj - * @return {boolean} - */ -export const isAbortError = object => { - return object[NAME] === 'AbortError'; -};