我有以下小提琴:
http://jsfiddle.net/thelgevold/3uv9nnjm/6/
angular.module('hello',[]).controller('helloController',function($q){
console.clear();
function someService(){
var deferred = $q.defer();
deferred.reject({e:'error'});
return deferred.promise;
}
function callService(){
return someService().then(function(obj){
console.log('first then');
}).
catch(function(e){
console.log('error1');
var deferred = $q.defer();
deferred.reject({e:'error'});
return deferred.promise;
});
}
callService().catch(function(e){
console.log('error2');
}).then(function(e){
console.log('second then');
});
});
它基本上只是一个快速的$ q承诺POC。我的问题是:为什么在承诺被拒绝时会调用last then子句?输出如下:
ERROR1
误差2
第二个
我理解为什么会打印error1 / error2,但我认为第二个字符串不应该被打印,因为承诺被拒绝了。我认为它会省略“第二个然后”,出于同样的原因,“第一个然后”被省略。
有什么想法吗?
在开始之前,不要这样做:
var deferred = $q.defer();
deferred.reject({e:'error'});
return deferred.promise;
做这个:
return $q.reject({e:'error'});
或者最好是这样:
return $q.reject(new Error('error'));
小心延迟反模式。
现在,回答你的问题。
该
.catch()
打电话给你
callService()
正在捕获错误并且不会产生新错误。它基本上“处理”了错误,以及以下内容
.then()
处理程序可以自由调用。
与您的示例等效的同步代码将是:
function someService() {
throw { e: 'error' };
}
function callService() {
try {
var obj = someService();
console.log('first then');
} catch (e) {
console.log('error1');
throw { e: 'error' };
}
}
var e;
try {
e = callService();
} catch (e) {
console.log('error2');
}
console.log('second then');
我认为,如果以这种方式看待它,它就非常有意义。
Promises / A +规范中的相关文本是 这里。出于所有意图和目的,您可以查看 catch
处理程序与a相同 onRejected
处理:
2.2.7。然后必须回复承诺[3.3]。
promise2 = promise1.then(onFulfilled, onRejected);
2.2.7.1。如果onFulfilled或onRejected返回值x,则运行Promise Resolution Procedure [[Resolve]](promise2,x)。
基本上,你的 onRejected
handler正在“返回”该值 undefined
,所以产生的承诺 catch()
用价值解决 undefined
。
在开始之前,不要这样做:
var deferred = $q.defer();
deferred.reject({e:'error'});
return deferred.promise;
做这个:
return $q.reject({e:'error'});
或者最好是这样:
return $q.reject(new Error('error'));
小心延迟反模式。
现在,回答你的问题。
该
.catch()
打电话给你
callService()
正在捕获错误并且不会产生新错误。它基本上“处理”了错误,以及以下内容
.then()
处理程序可以自由调用。
与您的示例等效的同步代码将是:
function someService() {
throw { e: 'error' };
}
function callService() {
try {
var obj = someService();
console.log('first then');
} catch (e) {
console.log('error1');
throw { e: 'error' };
}
}
var e;
try {
e = callService();
} catch (e) {
console.log('error2');
}
console.log('second then');
我认为,如果以这种方式看待它,它就非常有意义。
Promises / A +规范中的相关文本是 这里。出于所有意图和目的,您可以查看 catch
处理程序与a相同 onRejected
处理:
2.2.7。然后必须回复承诺[3.3]。
promise2 = promise1.then(onFulfilled, onRejected);
2.2.7.1。如果onFulfilled或onRejected返回值x,则运行Promise Resolution Procedure [[Resolve]](promise2,x)。
基本上,你的 onRejected
handler正在“返回”该值 undefined
,所以产生的承诺 catch()
用价值解决 undefined
。