chore: remove code duplication in custom errors (#842)

* remove code duplication in custom errors

* check using base class
This commit is contained in:
Konstantin Vyatkin 2020-06-10 07:17:35 -04:00 committed by GitHub
parent 1cb9070cce
commit 8f406b789a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 48 additions and 61 deletions

View File

@ -9,8 +9,9 @@ import Stream, {PassThrough} from 'stream';
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 {FetchError} from './errors/fetch-error.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

View File

@ -1,27 +1,10 @@
import {FetchBaseError} from './base.js';
/**
* Abort-error.js
*
* AbortError interface for cancelled requests
*/
/**
* 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
*/
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);
}
}

20
src/errors/base.js Normal file
View File

@ -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;
}
}

View File

@ -1,34 +1,26 @@
import {FetchBaseError} from './base.js';
/**
* @typedef {{ address?: string, code: string, dest?: string, errno: number, info?: object, message: string, path?: string, port?: number, syscall: string}} SystemError
*/
/**
* Fetch-error.js
*
* FetchError interface for operational errors
*/
/**
* 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
*/
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);
}
}

View File

@ -16,8 +16,8 @@ import {writeToStream} 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};

View File

@ -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';
};

View File

@ -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';