如何在switch语句中使用instanceof

时间:2016-03-31 11:51:27

标签: javascript error-handling ecmascript-6

我使用自定义错误(es6-error)允许我根据他们的类处理错误,如下所示:

import { DatabaseEntryNotFoundError, NotAllowedError } from 'customError';

function fooRoute(req, res) {
  doSomethingAsync()
    .then(() => {
      // on resolve / success
      return res.send(200);
    })
    .catch((error) => {
      // on reject / failure
      if (error instanceof DatabaseEntryNotFoundError) {
        return res.send(404);
      } else if (error instanceof NotAllowedError) {
        return res.send(400);
      }
      log('Failed to do something async with an unspecified error: ', error);
      return res.send(500);
    };
}

现在我更倾向于使用开关来实现这种类型的流程,结果如下:

import { DatabaseEntryNotFoundError, NotAllowedError } from 'customError';

function fooRoute(req, res) {
  doSomethingAsync()
    .then(() => {
      // on resolve / success
      return res.send(200);
    })
    .catch((error) => {
      // on reject / failure
      switch (error instanceof) {
        case NotAllowedError:
          return res.send(400);
        case DatabaseEntryNotFoundError:
          return res.send(404);
        default:
          log('Failed to do something async with an unspecified error: ', error);
          return res.send(500);
      }
    });
}
然而,

instanceof并不像那样工作。所以后者失败了。

有没有办法在switch语句中检查其类的实例?

3 个答案:

答案 0 :(得分:72)

一个不错的选择是使用对象的constructor property

// on reject / failure
switch (error.constructor) {
    case NotAllowedError:
        return res.send(400);
    case DatabaseEntryNotFoundError:
        return res.send(404);
    default:
        log('Failed to do something async with an unspecified error: ', error);
        return res.send(500);
}

请注意,constructor必须与创建对象的完全匹配(假设errorNotAllowedError的实例,NotAllowedError是{{1}的子类}}):

  • Errorerror.constructor === NotAllowedError
  • trueerror.constructor === Error

这与false不同,后者也可以与超类匹配:

  • instanceoferror instanceof NotAllowedError
  • trueerror instanceof Error

检查this interesting post关于true属性。

答案 1 :(得分:7)

解决方法,以避免if-else。找到here

switch (true) {
    case error instanceof NotAllowedError: 
        return res.send(400);

    case error instanceof DatabaseEntryNotFoundError: 
        return res.send(404);

    default:
        log('Failed to do something async with an unspecified error: ', error);
        return res.send(500);
}

答案 2 :(得分:0)

这种情况下的另一种选择是在错误的构造函数中仅具有一个状态字段。

例如,按如下所示构建错误:

class NotAllowedError extends Error {
    constructor(message, status) {
        super(message);
        this.message = message;
        this.status = 403; // Forbidden error code
    }
}

像这样处理错误:

.catch((error) => {
  res.send(error.status);
});