用Q.deferred捕获错误

我有一个nodeJS项目,我希望使用asynchronousfunction。 也就是说,我正在使用Q库。

我有一个叫做someFunction()的函数,我希望返回一个promise。 有了这个function,我就可以检查这个承诺是否已经解决或被拒绝了,如下所示:

someFunction() .then( function(results) { console.log("Success!"); }, function (error) { console.log("An error occurred, and I would wish to log it for example"); } ); 

我对上面的函数直观的预期是,错误函数会捕获所有可能的错误。 所以如果在someFunction内部引发一些exception,我可以放心,错误函数将会运行('then'之后的第二个函数)。 但似乎并非如此。

例如,假设someFunction将被定义如下:

 function someFunction() { var deferred = Q.defer(); throw new Error("Can't bar."); deferred.resolve("success"); } 

现在,如果我像调用上面的代码块一样调用someFunction()函数,它将不会运行错误函数。 这是为什么? Q.承诺错误的部分是不是错误? 为什么我应该手动拒绝发生的每一个错误? 我知道我可以将someFunction的全部内容设置为try / catch子句,然后拒绝这个延期的,但是那个感觉是错误的! 必须有更好的办法,我知道你们中有些人可以知道它!

有了这些信息,我开始思考deferred.reject和deferred.resolve是甚么意思呢? 这是否意味着要捕捉exception? 我真的应该手动通过所有的错误情况,并调用他们的deferred.reject? 我很想听听这个应该如何处理专业。

它不会运行错误function。 这是为什么?

因为你同步抛出一个exception,而不是返回一个承诺。 你从来不应该这样做 。

Q.承诺错误的部分要点是不是?

不, then在callback中隐式捕获exception,defferred不会 – 它们只是一个( 不赞成使用的 )API来创buildpromise。

为什么我应该手动拒绝发生的每一个错误?

因为asynchronous错误预计会传递给callback,而不是被抛出。

我知道我可以将someFunction的全部内容设置为try / catch子句,然后拒绝这个延期的,但是那个感觉是错误的! 一定会有更好的办法!

有: Q.Promise构造函数 ,标准(ES6)promise创buildAPI。 它具有能够从执行程序函数捕获同步exception的好处:

 function someFunction() { return new Q.Promise(function(resolve) { throw new Error("Can't bar."); resolve("success"); }); } 

Q具有成功和错误的特定function,所以使用:

 deferred.reject("error"); 

扔一个例外。

接下来的事情是, 一些function必须返回承诺,使用它时使用它:

 function someFunction() { var deferred = Q.defer(); try{ //some Asynchronous code deferred.resolve("success"); }catch(e){ deferred.reject(e.message); } return deffered.promise; //return promise to use then } 

因为承诺不是魔术。 他们不会奇迹般地捕捉错误。 他们捕捉它们,因为它们将try..catch-blocks中的callback包装到callback中,将错误转换为拒绝的Promise。

如果你想让一个错误被Promise链处理,那么把函数调用放到一个promise链中: Q.resolve().then(someFunction).then(...) 。 现在在某些函数中发生的任何同步错误都可以在下面的处理。

顺便说一句:如果你使用Q.defer(),而你没有处理一些callback式的API,你肯定是做错了。 search延迟反模式。

抛出一个错误会阻止代码执行(并将closures节点),除非您在try / catch块中捕获错误。

可以通过使用deferred.reject(error)将处理的来自请求的错误传递给.catch链。 代码错误和自定义抛出的错误需要在try / catch中处理,这是处理这种错误的正确方法。

 function someFunction() { var deferred = Q.defer(); deferred.reject("Can't bar."); // or try { throw new Error("Can't bar."); } catch(err) { deferred.reject("Can't bar."); } deferred.resolve("success"); }