【问题标题】:Generic promise retry logic通用承诺重试逻辑
【发布时间】:2018-10-20 02:14:44
【问题描述】:

我正在尝试弄清楚如何创建一个通用的重试函数,该函数会以指数方式回退传递给它的任何承诺。看起来一切正常,除了几件事。如果函数在第一次尝试时解析,那么我会看到我的解析值,它会注销嘿,这是预期的。如果它在任何后续调用中解决,它不会注销嘿。如果它拒绝,我会收到一些我尚未调查的弃用警告。这是代码...

function retry(func, max, time) {
    console.log(max);
    return new Promise((resolve, reject) => {
        func()
            .then(r => resolve(r))
            .catch(err => {
                if (max === 0) {
                    reject(err);
                } else {
                    setTimeout(function(){
                        retry(func, --max, time * 2);
                    }, time);
                }
            });
    });
}

const promise = retry(function () {
    return new Promise((resolve, reject) => {
        const rand = Math.random();
        if (rand >= 0.8) {
            resolve('hey');
        } else {
            reject(new Error('oh noes'));
        }
    });
}, 5, 100);

promise.then(r => console.log(r)).catch(err => console.log(err));

任何帮助将不胜感激。

【问题讨论】:

  • 当你重试时,你永远不会真正解决原来的承诺。
  • @SLaks 在实际执行的函数解决之前,我不想解决任何问题。您能准确告诉我代码中需要更改的内容吗?
  • 当你调用retry()时,你需要在它完成后解决原来的promise(通过调用resolve()
  • @SLaks 我试图在几个不同的地方调用 resolve() ,但仍然没有得到它。 :(你能说得更具体点吗?

标签: javascript node.js asynchronous promise


【解决方案1】:

这是一个工作示例

/**
 * Function to retry
 */
function retry(func, max, time) {
  return new Promise((resolve, reject) => {
    apiFunction()
      .then(resolve)
      .catch(err => {
        if (max === 0) {
          return reject(err);
        } else {
          setTimeout(function() {
            retry(func, --max, time * 2)
              .then(resolve)
              .catch(reject);
          }, time);
        }
      });
  });
}

/**
 * Function to test out
 */
const apiFunction = () => new Promise((resolve, reject) => {
  const rand = Math.random();

  if (rand >= 0.8) {
    console.log('Works');
    
    resolve('hey');
  } else {
    console.log('fail');
    
    reject(new Error('oh noes'));
  }
});

retry(apiFunction, 5, 10)
  .then(() => console.log('all done ok'))
  .catch(() => console.log('all done error'));

【讨论】:

  • 您先生,是人中的神。谢谢!
猜你喜欢
  • 2020-08-09
  • 1970-01-01
  • 2017-02-03
  • 2016-10-25
  • 1970-01-01
  • 1970-01-01
  • 2017-03-21
  • 2018-07-19
  • 1970-01-01
相关资源
最近更新 更多