Best way to schedule asynchronous HTTP requests #654
-
I have a situation where I need to send asynchronous requests every few seconds to several URLs that are in a list. I found out that import asyncio
import aiohttp
import time
from codetiming import Timer
async def fetch(url, session) -> str:
async with session.get(url) as resp:
return await resp.text()
async def main():
urls = [url1, url2, ...]
update_interval = 3
start_time = time.time()
while True:
tasks = []
async with aiohttp.ClientSession() as session:
for url in urls:
tasks.append(asyncio.create_task(fetch(url, session)))
resp = await asyncio.gather(*tasks, return_exceptions=True)
time.sleep(update_interval - ((time.time() - start_time) % update_interval))
with Timer(text='Elapsed time: {:.2f}'):
asyncio.run(main()) The above code works fine until, for whatever reason, there is a problem requesting one or more URLs. So, I thought I need a scheduler to do the job and I found AsyncScheduler useful for doing jobs asynchronously, however, I don't have any idea how I can use it to request multiple links. I would appreciate it if one can help me in this regard. |
Beta Was this translation helpful? Give feedback.
Replies: 3 comments 7 replies
-
Is there a reason why you felt aiohttp was superior to httpx? I can give you a simple example involving httpx and AnyIO (which it relies on): from __future__ import annotations
import asyncio
from anyio import create_task_group
from httpx import AsyncClient, HTTPError
async def main() -> None:
urls = ["https://example.org/", "https://github.com/"]
responses: list[str] = []
update_interval = 3
async def fetch(url: str) -> None:
try:
resp = await http.get(url)
except HTTPError as exc:
print(f"Error fetching {url}: {exc}")
else:
responses.append(resp.text)
loop = asyncio.get_running_loop()
async with AsyncClient() as http:
while True:
start_time = loop.time()
async with create_task_group() as tg:
for url in urls:
tg.start_soon(fetch, url)
print("----------------\n".join(responses))
responses.clear()
sleep_time = max(update_interval - (loop.time() - start_time), 0)
await asyncio.sleep(sleep_time)
asyncio.run(main()) I can make another example that uses |
Beta Was this translation helpful? Give feedback.
-
Since there is no option to make replies as accepted answers, I referenced your good points here again. |
Beta Was this translation helpful? Give feedback.
-
Hi, i'm tryining to implement this code for my purpose. I've some issue on his line: from apscheduler.schedulers.async_ import AsyncScheduler. My terminal shows: apscheduler.schedulers.async_ could not be resolved. Can I resolve it? |
Beta Was this translation helpful? Give feedback.
Since there is no option to make replies as accepted answers, I referenced your good points here again.