У меня есть асинхронный блок:
test().then(function(result){
// Success: Do something.
doSomething();
}).catch(function(error){
// Error: Handle the error, retry!
// How to re-run this whole block?
});Я могу отслеживать результаты success и failed. Однако можно ли повторить попытку всей цепочки test().then().catch() в случае неудачи? И продолжать попытки, пока проблема не исчезнет?
Обратите внимание, что вы должны установить ограничение на частоту повторных попыток или даже задержку отката, чтобы вы не попали в бесконечный цикл и, возможно, не перегрузили любой ресурс в test или doSomething, который выходит из строя.
Например, используя setTimeout()?
Да, что-то такое



![Безумие обратных вызовов в javascript [JS]](https://i.imgur.com/WsjO6zJb.png)


Вы можете поместить все это в функцию, которая рекурсивно вызывает себя, если вводится блок catch:
function tryTest() {
return test().then(function(result) {
// Success: Do something.
doSomething();
}).catch(function(error) {
// error handling
// make sure to return here,
// so that the initial call of tryTest can know when the whole operation was successful
return tryTest();
});
}
tryTest()
.then(() => {
console.info('Finished successfully');
});
Если ваш doSomething может принимать аргумент result, и если tryTest не принимает никаких аргументов, вы можете упростить приведенное выше до:
function tryTest() {
return test()
.then(doSomething)
.catch(tryTest);
}
tryTest()
.then(() => {
console.info('Finished successfully');
});
Вы можете поместить это в функцию.
function dbug() {
test().then(function(result){
// Success: Do something.
doSomething();
}).catch(function(error){
// Error: Handle the error, retry!
dbug()
});
}
Если вы можете переключиться на синтаксис async/await, вы можете использовать цикл while:
let keepTrying;
do {
try {
await test();
keepTrying = false;
} catch {
keepTrying = true;
}
} while (keepTrying)
doSomething();
Затем вы можете абстрагировать логику повторных попыток в ее собственную функцию для повторного использования.
Предполагая, что все дело в повторной отправке запроса на какой-то ошибочный / раздутый сторонний API
Если это производственный вопрос, скорее, образовательный, я бы предложил поискать стороннюю библиотеку, которая реализует это самостоятельно.
Скажем, для axios есть хороший axios-retry.
Почему? Предположим, вы можете подумать, что есть только один случай, когда API говорит, что возвращает 502. Но на самом деле случаев гораздо больше, о чем лучше помнить:
Самостоятельно написать такую логику было бы излишним. И попытка использовать самое простое решение может поразить вас, когда вы этого не ожидаете.
PS также в качестве бонуса вы сможете настроить все запросы к определенному API с помощью одного фрагмента, как это происходит для пользовательских экземпляров axios (и я считаю, что должны быть другие плагины для альтернативных библиотек)
Поместите это в функцию. Назови это.