Write a decorator factory retry(times, exceptions):
times times in total.exceptions (a tuple of exception classes),
try again; any other exception propagates immediately.__name__ (use functools.wraps).The harness decorates a flaky function that fails a given number of times and reports what happened.
Implement retry. Input: times: int, exceptions: tuple[type[BaseException], ...]. Returns: a decorator.
Fails twice, succeeds on the third call.
This code runs before yours (fake clients, clocks and the test harness). You can use its names; don't edit them.
class TransientError(Exception):
pass
class FatalError(Exception):
pass
def __harness__(retry, times, failures, kind):
calls = {"n": 0}
error = {"transient": TransientError, "fatal": FatalError}[kind]
def flaky(x):
"""Fails `failures` times, then returns x * 2."""
calls["n"] += 1
if calls["n"] <= failures:
raise error(f"attempt {calls['n']}")
return x * 2
wrapped = retry(times, (TransientError,))(flaky)
try:
result = wrapped(21)
outcome = {"result": result}
except Exception as exc:
outcome = {"raised": type(exc).__name__, "message": str(exc)}
outcome["calls"] = calls["n"]
outcome["name"] = getattr(wrapped, "__name__", None)
return outcome
import functools
def retry(times: int, exceptions: tuple):
def decorator(fn):
return fn
return decorator
Run executes the public tests. Submit grades against public and hidden tests.
Write a decorator factory retry(times, exceptions):
times times in total.exceptions (a tuple of exception classes),
try again; any other exception propagates immediately.__name__ (use functools.wraps).The harness decorates a flaky function that fails a given number of times and reports what happened.
Implement retry. Input: times: int, exceptions: tuple[type[BaseException], ...]. Returns: a decorator.
Fails twice, succeeds on the third call.
This code runs before yours (fake clients, clocks and the test harness). You can use its names; don't edit them.
class TransientError(Exception):
pass
class FatalError(Exception):
pass
def __harness__(retry, times, failures, kind):
calls = {"n": 0}
error = {"transient": TransientError, "fatal": FatalError}[kind]
def flaky(x):
"""Fails `failures` times, then returns x * 2."""
calls["n"] += 1
if calls["n"] <= failures:
raise error(f"attempt {calls['n']}")
return x * 2
wrapped = retry(times, (TransientError,))(flaky)
try:
result = wrapped(21)
outcome = {"result": result}
except Exception as exc:
outcome = {"raised": type(exc).__name__, "message": str(exc)}
outcome["calls"] = calls["n"]
outcome["name"] = getattr(wrapped, "__name__", None)
return outcome
import functools
def retry(times: int, exceptions: tuple):
def decorator(fn):
return fn
return decorator
Run executes the public tests. Submit grades against public and hidden tests.