19
19
def retry_connection_error (
20
20
attempts : int = DEFAULT_ATTEMPTS ,
21
21
exception : type [Exception ] = aiohttp .ClientError ,
22
+ backoff : float | None = None ,
22
23
) -> Callable [[Callable [P , Awaitable [T ]]], Callable [P , Awaitable [T ]]]:
23
24
"""Define a wrapper to retry on connection error."""
25
+ if backoff is None :
26
+ backoff = BACKOFF_TIME
24
27
25
28
def _decorator_retry_connection_error (
26
29
func : Callable [P , Awaitable [T ]],
@@ -35,8 +38,17 @@ def _decorator_retry_connection_error(
35
38
async def _async_wrap_connection_error_retry ( # type: ignore[return]
36
39
* args : P .args , ** kwargs : P .kwargs
37
40
) -> T :
41
+ logger .debug (
42
+ "retry_connection_error wrapper called for %s with exception=%s, attempts=%s" ,
43
+ func .__name__ ,
44
+ exception ,
45
+ attempts ,
46
+ )
38
47
for attempt in range (attempts ):
39
48
try :
49
+ logger .debug (
50
+ "Attempt %s/%s for %s" , attempt + 1 , attempts , func .__name__
51
+ )
40
52
return await func (* args , ** kwargs )
41
53
except exception as ex :
42
54
#
@@ -49,16 +61,25 @@ async def _async_wrap_connection_error_retry( # type: ignore[return]
49
61
# to close the connection at any time, we treat this as a normal and try again
50
62
# once since we do not want to declare the camera as not supporting PullPoint
51
63
# if it just happened to close the connection at the wrong time.
64
+ logger .debug (
65
+ "Caught exception %s (type: %s) on attempt %s/%s" ,
66
+ ex ,
67
+ type (ex ).__name__ ,
68
+ attempt + 1 ,
69
+ attempts ,
70
+ exc_info = True ,
71
+ )
52
72
if attempt == attempts - 1 :
73
+ logger .debug ("Final attempt failed, re-raising exception" )
53
74
raise
54
75
logger .debug (
55
76
"Error: %s while calling %s, backing off: %s, retrying..." ,
56
77
ex ,
57
78
func ,
58
- BACKOFF_TIME ,
79
+ backoff ,
59
80
exc_info = True ,
60
81
)
61
- await asyncio .sleep (BACKOFF_TIME )
82
+ await asyncio .sleep (backoff )
62
83
63
84
return _async_wrap_connection_error_retry
64
85
0 commit comments