Currently, on_exception takes an argument exception: _MaybeSequence[Type[Exception]].
However, this cannot handle any Sequence of Type[Exception]. For instance, if a list[Type[Exception]] is given, as in the following code:
import backoff
i: int = 0
@backoff.on_exception(backoff.expo, [ValueError])
def _retry():
global i
i += 1
print(f"i = {i}")
if i < 3:
raise ValueError(f"failure {i}")
if i == 3:
raise RuntimeError("runtime error")
return "success"
_retry()
then a hard-to-understand stack trace is generated:
i = 1
Traceback (most recent call last):
File "/Users/davidslater/git/litl/backoff/backoff/_sync.py", line 107, in retry
ret = target(*args, **kwargs)
File "/Users/davidslater/git/litl/backoff/script.py", line 10, in _retry
raise ValueError(f"failure {i}")
ValueError: failure 1
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/Users/davidslater/git/litl/backoff/script.py", line 16, in <module>
_retry()
File "/Users/davidslater/git/litl/backoff/backoff/_sync.py", line 108, in retry
except exception as e:
TypeError: catching classes that do not inherit from BaseException is not allowed
Similar issues can also arise with the same traceback, such as:
@backoff.on_exception(backoff.expo, ValueError())
which are hard to understand and debug, as there are no lines between the function call in user code and the except exception as e in the library.
I see two major different ways to improve this:
A) modify the type information. If done directly, this would change the type to Union[Type[Exception], Tuple[Type[Exception]]],
Alternatively, you could add to _typing.py:
_MaybeTuple = Union[T, Tuple[T]]
and then change the type to _MaybeTuple[Type[Exception]].
B) Do checking of exception when it is given to the function to improve error response. Essentially, just check if it is an Exception or a tuple of exception types and raise a ValueError if not.
Currently,
on_exception
takes an argumentexception: _MaybeSequence[Type[Exception]]
.However, this cannot handle any
Sequence
ofType[Exception]
. For instance, if alist[Type[Exception]]
is given, as in the following code:then a hard-to-understand stack trace is generated:
Similar issues can also arise with the same traceback, such as:
which are hard to understand and debug, as there are no lines between the function call in user code and the
except exception as e
in the library.I see two major different ways to improve this: A) modify the type information. If done directly, this would change the type to
Union[Type[Exception], Tuple[Type[Exception]]],
Alternatively, you could add to_typing.py
:and then change the type to
_MaybeTuple[Type[Exception]]
.B) Do checking of
exception
when it is given to the function to improve error response. Essentially, just check if it is an Exception or a tuple of exception types and raise a ValueError if not.