【问题标题】:Why is instanceof in TypeScript not working for inherited class? [duplicate]为什么 TypeScript 中的 instanceof 不适用于继承的类? [复制]
【发布时间】:2019-09-22 23:57:42
【问题描述】:

我有以下课程:

class ApiError extends Error {
    httpCode: number
    constructor(message:string, httpCode:number = 400) {
        super(message);
        this.httpCode = httpCode;
    }
}

export class ErrorForbidden extends ApiError {
    constructor(message:string = 'Forbidden') {
        super(message, 403);
    }
}

然后我像这样创建一个实例:

const error = new ErrorForbidden();
console.info(error instanceof ErrorForbidden); // false
console.info(error instanceof Error); // true

所以它似乎检测到它是 Error 的实例,但不是 ErrorForbidden 的实例,即使我是这样创建它的。

知道为什么它不起作用吗?以及如何让它发挥作用?

【问题讨论】:

    标签: typescript instanceof


    【解决方案1】:

    如果您将 TypeScript 设置为编译为 ES5 或其他一些 ES2015 之前的 JavaScript 版本,TypeScript 无法正确子类化 Error,因为在 ES2015 之前不可能这样做。因此,它会产生 Error 但不是 ErrorForbidden(在您的情况下)。

    如果设置为 ES5 输出,则为您的代码生成的 JavaScript(如果我省略了 export 以便在 Playground 中使用它)看起来像这样:

    "use strict";
    var __extends = (this && this.__extends) || (function () {
        var extendStatics = function (d, b) {
            extendStatics = Object.setPrototypeOf ||
                ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
                function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
            return extendStatics(d, b);
        };
        return function (d, b) {
            extendStatics(d, b);
            function __() { this.constructor = d; }
            d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
        };
    })();
    var ApiError = /** @class */ (function (_super) {
        __extends(ApiError, _super);
        function ApiError(message, httpCode) {
            if (httpCode === void 0) { httpCode = 400; }
            var _this = _super.call(this, message) || this;
            _this.httpCode = httpCode;
            return _this;
        }
        return ApiError;
    }(Error));
    var ErrorForbidden = /** @class */ (function (_super) {
        __extends(ErrorForbidden, _super);
        function ErrorForbidden(message) {
            if (message === void 0) { message = 'Forbidden'; }
            return _super.call(this, message, 403) || this;
        }
        return ErrorForbidden;
    }(ApiError));
    var error = new ErrorForbidden();
    console.info(error instanceof ErrorForbidden); // false
    console.info(error instanceof Error); // true
    

    ...显示falsetrue

    Live on the Playground

    设置为 ES2015 输出时与此比较:

    "use strict";
    class ApiError extends Error {
        constructor(message, httpCode = 400) {
            super(message);
            this.httpCode = httpCode;
        }
    }
    class ErrorForbidden extends ApiError {
        constructor(message = 'Forbidden') {
            super(message, 403);
        }
    }
    const error = new ErrorForbidden();
    console.info(error instanceof ErrorForbidden); // false
    console.info(error instanceof Error); // true
    

    ...显示truetrue

    Live on the Playground

    【讨论】:

      猜你喜欢
      • 2012-12-23
      • 1970-01-01
      • 1970-01-01
      • 2010-09-07
      • 2011-10-14
      • 1970-01-01
      • 1970-01-01
      • 2017-01-24
      • 2016-06-28
      相关资源
      最近更新 更多