首页 > 解决方案 > 开玩笑断言承诺递归

问题描述

我有这个异步函数可以在某些条件下重试承诺。

async function retry(f, interval = 1000, retries = 10) {
try {
  return await f
} catch (e) {
  if (retries == 0) {
    throw e
  }

  setTimeout(() => {
    retry(f, Math.min(60000, interval * 2), retries - 1);
  }, interval);
}

}

我想用 jest 断言递归执行的次数,直到函数被抛出。这是函数调用。

const f = new Promise((resolve, reject) => reject('test'))

retry(f)

标签: javascriptjestjs

解决方案


f应该是重试时可以调用的函数。APromise只会解决/拒绝一次,然后保持该状态。使用一个函数可以让你重做你想尝试的事情。

Whenf是一个函数,它本身可以是一个闭包,计算它被调用的次数。例如:

function delay(t) {
  return new Promise(resolve => {
    setTimeout(resolve, t);
  });
}
async function retry(f, interval = 100, retries = 10) {
  try {
    return await f();
  } catch (e) {
    if (retries == 0) {
      throw e;
    }
    await delay(interval);
    return retry(f, Math.min(60000, interval * 2), retries - 1);
  }
}

describe("retry", () => {
  it("retries 10 times", async () => {
    let count = 0;
    const f = () => {
      count++;
      return Promise.reject(`test ${count}`);
    };

    try {
      await retry(f);
    } catch (e) {
      // expect the last exception to be thrown
      expect(e).toEqual("test 11");
    }
    // 10 retries + first try = 11
    expect(count).toBe(11);
  });
});

推荐阅读