22 lines
653 B
Python
22 lines
653 B
Python
import asyncio
|
|
from typing import Awaitable, Callable, TypeVar
|
|
|
|
from app.core.constants import MAX_RETRIES
|
|
|
|
T = TypeVar("T")
|
|
|
|
|
|
class RetryExecutor:
|
|
async def run(self, operation: Callable[[], Awaitable[T]]) -> T:
|
|
last_error: Exception | None = None
|
|
for attempt in range(1, MAX_RETRIES + 1):
|
|
try:
|
|
return await operation()
|
|
except (TimeoutError, ConnectionError, OSError) as exc:
|
|
last_error = exc
|
|
if attempt == MAX_RETRIES:
|
|
break
|
|
await asyncio.sleep(0.1 * attempt)
|
|
assert last_error is not None
|
|
raise last_error
|