There's the function make_request that makes http request to the API. And I can't make more than 3 requests per second.
I did something like that
coroutines = [make_request(...) for ... in ...]
tasks = []
for coroutine in coroutines:
tasks.append(asyncio.create_task(coroutine))
await asyncio.sleep(1 / 3)
responses = asyncio.gather(*tasks)
But also I can't make more than 1000 requests per hour. (Probably, I could make delay 3600 / 1000.) And what if the internet connection will be lost? I should try to make request again.
I can wrap make_request like that:
async def try_make_request(...):
while True:
try:
return await make_request(...)
exception APIError as err:
logging.exception(...)
In this case, it's possible that more than 3 requests per second will be made.
I found that solution but I'm not sure that this is the best solution
pending = []
coroutines = [...]
for coroutine in coroutines:
pending.append(asyncio.create_task(coroutine))
await asyncio.sleep(1 / 3)
result = []
while True:
finished, pending = await asyncio.wait(
pending, return_when=asyncio.FIRST_EXCEPTION
)
for task in finished:
exc = task.exception()
if isinstance(exc, APIError) and exc.code == 29:
pending.add(task.get_coro()) # since python 3.8
if exc:
logging.exception(...)
else:
result.append(task.result())
if not pending:
break