【问题标题】:How to retry fetch in a loop when it throws an error抛出错误时如何在循环中重试获取
【发布时间】:2020-06-03 00:06:46
【问题描述】:

我有以下JS函数:

func() {
  return fetch({
    ...
  }).then({
    ...
  })catch({
    ...
  })
}

在其中我返回一个由fetch() 返回的承诺。如果它失败(即调用catch() 块)我想重复整个事情。就像将整个事情放在 while (true) 循环中一样,但我不知道如何使用 Promise 来做到这一点。

有什么建议吗?

【问题讨论】:

标签: promise try-catch fetch es6-promise


【解决方案1】:

您可以简单地编写一个循环并计算尝试次数,直到一次成功或您用完为止。 async/await 让这一切变得简单。请参阅下面的一个最小的完整示例。

请注意,获取 API 使用 response.ok 标志来确保响应状态落在 200 范围内。用try/catch 包装仅足以覆盖连接失败。如果响应指示错误请求,则重试可能不合适。此代码在这种情况下解决了承诺,但您可以将 !response.ok 视为错误并根据需要重试。

const fetchWithRetry = async (url, opts, tries=2) => {
  const errs = [];
  
  for (let i = 0; i < tries; i++) {
    // log for illustration
    console.log(`trying GET '${url}' [${i + 1} of ${tries}]`);
    
    try {
      return await fetch(url, opts);
    }
    catch (err) {
      errs.push(err);
    }
  }
  
  throw errs;
};

fetchWithRetry("https://httpstat.us/400")
  .then(response => console.log("response is OK? " + response.ok))
  .catch(err => console.error(err));

fetchWithRetry("foo")
  .catch(err => console.error(err.map(e => e.toString())));

fetchWithRetry("https://httpstat.us/200")
  .then(response => response.text())
  .then(data => console.log(data))
  .catch(err => console.error(err));

如果您想要无限次重试,请将 tries 参数传递为 -1(但这对我来说似乎并不常见)。

【讨论】:

    【解决方案2】:

    你应该仔细看看 promises 和 async await。

    async function fetchUntilSucceeded() {
      let success = false;
      while(!success) {
        try {
          let result = await fetch(...);
          success = true;
          //do your stuff with your result here
        } catch {
          //do your catch stuff here
        }
      }
    }
    

    如果你只需要结果:

    async function fetchUntilSucceeded() {
      while(true) {
        try {
          return await fetch(...);
        } 
      }
    }
    

    但是要小心这样的代码,因为它可能永远无法解析!它还可以发送大量请求而无需任何等待时间。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-12-18
      • 2014-06-06
      • 2011-07-10
      • 2020-11-02
      • 2012-07-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多