Home > database >  Exponential Backoff test only tries once
Exponential Backoff test only tries once

Time:01-12

Trying to test an Exponential Backoff function, but it only appears to Catch once then return. I'm sure it's something simple, but what am I missing?

EB fn

function tryAgain(action, maxTries = 5) {
    for (let tries = 0; tries < maxTries; tries  ) {
      Logger.log(`Try number ${tries}`);
      try {
        return action();
      } catch (e) {
        Logger.log(`Error caught; trying again: ${e}`);
        if (tries = maxTries) { throw e; };
      }
      Utilities.sleep(2 ** tries * 1000)
    }
  }

test fn

function myFunction() {
  tryAgain(testTryAgain);
}

function testTryAgain() {
  Logger.log("test");
  throw "error msg"
}

CodePudding user response:

Use a more reliable exponential backoff implementation, like this:

function myFunction() {
  exponentialBackoff_(testTryAgain);
}

To supply arguments, use a closure, like this:

function myFunction() {
  const param = 1;
  const result = exponentialBackoff_(() => testTryAgain(param));
  console.log(result);
}

Here is a copy of the exponentialBackoff_() function from Exception: Failed to retrieve form data, including full JSDoc and attribution:

/**
* Calls a closure, retries on failure, and returns the value it gives.
*
* Usage:
*   exponentialBackoff_(myFunction);
*   // ...or:
*   exponentialBackoff_(() => myFunction(param1, param2));
*   // ...or:
*   const result = exponentialBackoff_(() => myFunction(param1, param2));
*   // ...or:
*   const respondentEmail = exponentialBackoff_(() => e.response.getRespondentEmail());
*
* @see https://en.wikipedia.org/wiki/Exponential_backoff
* @param {Function} action The closure to call.
* @param {Number} maxNumTries Optional. The number of times to retry. Defaults to 5.
* @return {Object} The closure return value.
*/
function exponentialBackoff_(action, maxNumTries = 5) {
  // version 1.0, written by --Hyde, 29 December 2022
  //  - see https://stackoverflow.com/a/74952372/13045193
  for (let tryNumber = 1; tryNumber <= maxNumTries; tryNumber  ) {
    try {
      return action();
    } catch (error) {
      if (tryNumber >= maxNumTries) {
        throw error;
      }
      Utilities.sleep(2 ** (tryNumber - 1) * 1000);
    }
  }
}
  • Related