def test_F_ValidLongIncreasingEndlessRetry(self):
        # [ F] endless_retry makes many valid increasing delays
        delays = phlsys_tryloop.make_default_endless_retry()

        first_secs = None
        last_secs = None
        for i in itertools.islice(delays, 1000):
            secs = i.total_seconds()
            self.assertGreaterEqual(secs, 0)
            self.assertTrue(last_secs is None or secs >= last_secs)
            if first_secs is None:
                first_secs = secs
            last_secs = secs

        self.assertGreater(last_secs, first_secs)
    def test_F_ValidLongIncreasingEndlessRetry(self):
        # [ F] endless_retry makes many valid increasing delays
        delays = phlsys_tryloop.make_default_endless_retry()

        first_secs = None
        last_secs = None
        for i in itertools.islice(delays, 1000):
            secs = i.total_seconds()
            self.assertGreaterEqual(secs, 0)
            self.assertTrue(last_secs is None or secs >= last_secs)
            if first_secs is None:
                first_secs = secs
            last_secs = secs

        self.assertGreater(last_secs, first_secs)
def critical_tryloop(f, identifier, detail):
    """Return the result of the supplied operation 'f', retry on exception.

    Will retry operation 'f' indefinitely until it does not raise, the delays
    used gradually increase so that whichever system is being tried is not
    overly stressed.

    :f: a callable that can be invoked like so 'f()'
    :identifier: a short string identifier for the calling line of code
    :detail: a string of the variables associated with the call, e.g. repo name
    :returns: the return value of operation 'f', if successful

    """
    def on_tryloop_exception(e, delay):
        abdt_logging.on_retry_exception(identifier, detail, e, delay)

    delays = phlsys_tryloop.make_default_endless_retry()

    return phlsys_tryloop.try_loop_delay(
        f, delays, onException=on_tryloop_exception)
def critical_tryloop(f, identifier, detail):
    """Return the result of the supplied operation 'f', retry on exception.

    Will retry operation 'f' indefinitely until it does not raise, the delays
    used gradually increase so that whichever system is being tried is not
    overly stressed.

    :f: a callable that can be invoked like so 'f()'
    :identifier: a short string identifier for the calling line of code
    :detail: a string of the variables associated with the call, e.g. repo name
    :returns: the return value of operation 'f', if successful

    """
    def on_tryloop_exception(e, delay):
        abdt_logging.on_retry_exception(identifier, detail, e, delay)

    delays = phlsys_tryloop.make_default_endless_retry()

    return phlsys_tryloop.try_loop_delay(
        f, delays, onException=on_tryloop_exception)