我正在兑现承诺。当我链许诺时,最后一个then
块不会执行。所有其他块都被执行,但是在最后一个承诺解决之后,什么也没有发生。有人可以向我解释我错过了什么吗?
var x = 1;
$(document).ready(function() {
getJobId(token).then(function(rsp) {
return rsp;
}).then(function(job_id) {
looper().then(function(rsp) {
console.log("app finished : " + rsp); // this block never gets called
});
});
});
function getJobId(token) {
// does an API call that returns a promise
return $.ajax({
url: "url"
});
}
function looper() {
return new Promise(function(resolve, reject) {
setTimeout(function() {
// if the call is successful
if (x == 5) {
resolve(1); // returns the value 1
} else {
x++; // we increment the value of the counter
console.log("not solved yet");
looper(); // we call the same function again
}
}, 5000); // (waits for 5 seconds)
});
}
答案 0 :(得分:2)
问题是您永远无法解决正在等待的承诺,即looper
返回的第一承诺。
您必须始终解决或拒绝一项承诺,或使其依赖于另一个。在这种情况下,要做的最小更改是通过将后续looper
的承诺传递到resolve
来使较早的依赖于后一个:
resolve(looper()); // we call the same function again
但这不是我要做的。相反,我自己不会looper
自称。我会让它直接处理事情:
function looper() {
function loop(resolve, reject) {
setTimeout(function() {
// if the call is successful
if (x == 5) {
resolve(1); // returns the value 1
} else {
x++; // we increment the value of the counter
console.log("not solved yet");
loop(resolve, reject);
}
}, 5000); // (waits for 5 seconds)
}
return new Promise(loop);
}
作为一个单独的问题,您不处理故障。这样做很重要。在这种情况下,可能在looper.then
处理程序中返回来自ready
的promise并添加一个catch
:
var x = 1;
$(document).ready(function() {
getJobId(token).then(function(rsp) {
return rsp;
}).then(function(job_id) {
return looper().then(function(rsp) {
console.log("app finished : " + rsp); // this block never gets called
});
}).catch(function(error) {
// Handle/report error here
});
});
function getJobId(token) {
// does an API call that returns a promise
return $.ajax({
url: "url"
});
}
function looper() {
function loop(resolve, reject) {
setTimeout(function() {
// if the call is successful
if (x == 5) {
resolve(1); // returns the value 1
} else {
x++; // we increment the value of the counter
console.log("not solved yet");
loop(resolve, reject);
}
}, 5000); // (waits for 5 seconds)
}
return new Promise(loop);
}
注释2:由于您使用的是Promise
,因此我认为您的目标是现代环境。在这种情况下,您可以考虑使用fetch
(返回一个本机承诺),而不是使用$.ajax
,后者返回一个与Promise兼容的jQuery jqXHR
对象。