我正在使用promises来重试API请求,如果它们失败了。我这样使用它:
var promise = new Promise((resolve, reject) => {
client.ApiRequest(params, function(data) {
if (!Array.isArray(data)) {
console.log("There was an error with the request.");
reject("Rate Limit Exceeded");
return;
}
...
resolve();
});
});
Utils.retry(promise, 1500);
然后Utils.retry方法如下:
static delay(delayMS) {
return new Promise(function(resolve, reject){
setTimeout(resolve, delayMS);
});
}
static retry(operation, delayMS) {
return operation.catch((err) => {
console.log(err);
return Utils.delay(delayMS).then(function(){
return Utils.retry(operation, delayMS)
});
});
}
如您所见,它从承诺中捕获reject()
并使用delay()
等待重试之前。代码运行,但似乎一旦承诺一直陷入被拒绝状态,承诺就会失败。
例如,当它失败时,它会延迟,然后重试承诺只是为了输出相同的拒绝消息。但是,在第一个函数中,它不会在后续重试时打印出“请求有错误”消息,因此我认为它甚至不会重试。
有没有办法重置这个promise状态,以便在重试时它会执行promise函数中的所有代码?
答案 0 :(得分:1)
不要传递对原始承诺的引用。 每次传递新承诺。以下是您可以做到的。
// a function that returns a new promise
var createPromise = function() {
return new Promise((resolve, reject) => {
client.ApiRequest(params, function(data) {
if (!Array.isArray(data)) {
console.log("There was an error with the request.");
reject("Rate Limit Exceeded");
return;
}
...
resolve();
});
});
}
-
static delay(delayMS) {
return new Promise(function(resolve, reject){
setTimeout(resolve, delayMS);
});
}
static retry(operation, delayMS) {
return operation().catch((err) => { //invoke the promise function
console.log(err);
return Utils.delay(delayMS).then(function(){
return Utils.retry(operation, delayMS)
});
});
}
Utils.retry(promise, 1500);
答案 1 :(得分:0)
它会给你相同的结果,因为你传递相同的,已经被拒绝的,答应你的重试处理程序。您需要创建一个新的承诺,以便返回重试处理程序,以使其正常工作。
这意味着你可能需要修改重试处理程序以接受promise工厂(一个返回你想要的promise的函数),而不是promise本身。所以你可以修改你的代码:
// Make function to return this promise instead:
var makePromise = () => {
return new Promise((resolve, reject) => {
client.ApiRequest(params, function(data) {
if (!Array.isArray(data)) {
console.log("There was an error with the request.");
reject("Rate Limit Exceeded");
return;
}
...
resolve();
});
});
};
Utils.retry(makePromise, 1500);
-
static delay(delayMS) {
return new Promise(function(resolve, reject){
setTimeout(resolve, delayMS);
});
}
static retry(operation, delayMS) {
// Note the () after operation. This function now expects operation
// to be a function that returns a promise.
return operation().catch((err) => {
console.log(err);
return Utils.delay(delayMS).then(function(){
return Utils.retry(operation, delayMS)
});
});
}