JS:处理多个顺序失败的异步请求

时间:2018-03-27 21:48:21

标签: javascript promise try-catch

我正在使用承诺(等待)。我有一个异步函数,必须等待异步请求:例如一个http请求。 HTTP请求可能会失败(超时或其他动机),但我需要回忆它直到成功或直到最大尝试次数(假设n次尝试),然后继续执行该功能。 我无法找到干净,井井有条的方法来做到这一点。 在伪代码下面:

async function func(){
  //DO something before HTTP request
  try{
    let res = await http_request();
  } catch(e){
    //http request failed
    //WHAT TO DO HERE TO CALL AGAIN THE HTTP REQUEST until success??
    //or until max attempts == n?
  }
  //DO other stuff only after the http request succeeded
  return;
}

这个想法是在最后返回一个promise,如果http请求和其余代码成功则解析,如果http请求尝试失败n次或其他错误,则拒绝。

PS:http请求是一个示例,但http_request()可以替换为任何其他异步函数。

3 个答案:

答案 0 :(得分:2)

你可以做一个while循环,一旦成功请求就会中断,否则再次尝试。计数器可用于限制尝试次数。

async function func(){
  let counter = 0;
  while (counter < 100) {
    try{
      let res = await http_request();
      break;
    } catch(e){
      counter++
      continue;
    }
  }
  return;
}

答案 1 :(得分:2)

您可以再次调用您的函数重试,然后您可以将其传递给重试计数器。您还应该在重试之前插入一个短暂的延迟,以避免锤击繁忙的服务器。

function delay(t, v) {
   return new Promise(resolve => {
       setTimeout(resolve.bind(null, v), t);
   });
}

const kMaxAttempts = 10;
const kDelayBeforeRetry = 500;

async function func(cntr = 0){
  //DO something before HTTP request
  ++cntr;
  try{
    let res = await http_request();
    //DO other stuff only after the http request succeeded
    return finalValue;
  } catch(e){
    // test to see if max retries have been exceeded
    // also examine e to see if the error is retryable
    if (cntr > kMaxAttempts || e is not a retryable error) {
        throw e;
    }
    // retry after a short delay
    return delay(kDelayBeforeRetry, cntr).then(func);

  }
}

答案 2 :(得分:0)

我会以不同的方式对待请求。你试图只捕捉一个错误。您还需要处理失败的响应。哪个曾经请求您使用的API,http_request()很可能会返回响应和错误对象。您可以使用response.status === 500等检查失败的请求。如果响应因任何原因失败,您可以重试该请求。我经常看到这样做

http_request.GET(URL).then((response, error) => {
  if (error) // retry
  else if (response.status === 200 && response.body) // success
  else if (response.status === 500) // retry
})

对于实际代码,您可以创建一个可重用的请求函数来执行if / else错误处理并获取HTTP方法和一些选项和数据等,并返回您的数据或错误的承诺 - 这是另一个共同模式。