如何处理承诺错误?

时间:2014-02-15 16:05:47

标签: javascript node.js error-handling promise bluebird

作为节点程序员。我习惯使用“nodebacks”来处理代码中的错误:

myFn(param, function(err, data) {
    if (err){
        //error handling logic
     }
     else {
        // business logic
    }
});

在编写该函数时,我可以执行以下操作:

var myFn = function(param, callback){
    var calc = doSomeCalculation(param);
    if(calc === null) { // or some other way to detect error
        callback(new Error("error with calculation"), null);
    }
    ...
    someAsyncOp(calcN,function(err, finalResult){
        if(err) return callback(err, null);
        callback(null, finalResult); // the error is null to signal no error
    });

};

我如何使用promises进行此类错误处理?

2 个答案:

答案 0 :(得分:40)

经验法则

每当你对如何用promises做某事表示怀疑时 - 想想同步版本。

try{
   var result = myFn(param);
   // business logic with result
} catch(e) {
    //error handling logic
}

至少在我看来,它比使用第一个参数(有时为null的回调更清晰。

承诺方式几乎总是非常类似于问题的同步版本:

myFn(param).then(function(result){
    // business logic with result
}).catch(function(e){
    //error handling logic
});

myFn看起来像处理回调时的情况:

var myFn = function(param){
    return new Promise(function(resolve, reject){
        var calc = doSomeCalculation(param);
        if(calc === null) { // or some other way to detect error
            reject(new Error("error with calculation"), null);
        }
        someAsyncOp(calcN,function(err, finalResult){
            if(err) reject(err);
            resolve(finalResult);
        })
    });
};

使用回调/节点回送

这只是你在使用回调时应该做的事情,当使用promises时它更简单,你可以这样做:

var myFn = function(param){
    var calc = doSomeCalculation(param);
    ...
    return someAsyncOp(calcN); // returning a promise.
}

此外,在承诺链内部工作时,您会得到安全保障:

myFn(param).then(function(calcN){
   // here, you throw to raise an error and return to resolve
   // new Promise should be used only when starting a chain.
}).catch(function(err){
    // handle error
}).then(function(){
   // ready to go again, we're out of the catch
});

请注意,某些类似BluebirdRSVPQ的库提供语法糖和方法的自动默认,因此您很少需要自己使用new Promise

另外,请考虑阅读thisthat以了解有关承诺错误处理的更多信息。

答案 1 :(得分:0)

如果您使用的是async / await语法,则可以仅使用常规的try-catch语法进行错误处理。

// your promise function
const myFn = function(param){
  return new Promise(function(resolve, reject){
      if (someLogic()) {
          resolve(someValue);
      } else {
          reject('failure reason');
      }
  });
}

// Define the parent function as an async function
async function outerFn(param) {
    try {
        // Wait for the promise to complete using await
        const result = await myFn(param)
        // business logic with result
    } catch (e) {
        //error handling logic
    }
}