Sanic-like background tasks
See original GitHub issueFirst Check
- I added a very descriptive title to this issue.
- I used the GitHub search to find a similar issue and didn’t find it.
- I searched the FastAPI documentation, with the integrated search.
- I already searched in Google “How to X in FastAPI” and didn’t find any information.
- I already read and followed all the tutorial in the docs and didn’t find an answer.
- I already checked if it is not related to FastAPI but to Pydantic.
- I already checked if it is not related to FastAPI but to Swagger UI.
- I already checked if it is not related to FastAPI but to ReDoc.
Commit to Help
- I commit to help with one of those options 👆
Example Code
# this is part of a Sanic application code
# please read description/wanted code for details
async def poll_for_config_updates(app):
polling_interval = app.config.CONFIG_UPDATE_POLL_INTERVAL # e.g. 60s
while True:
await app.ctx.config_registry.update_configs()
await asyncio.sleep(polling_interval)
@app.before_server_start
async def get_configs(app, loop):
app.add_task(poll_for_config_updates)
Description
In Sanic, the concept of a background task refers to something different than in FastAPI – namely, the ability to add a task to the event loop outside of the request/response concept, such as on server start.
From Sanic docs:
async def notify_server_started_after_five_seconds():
await asyncio.sleep(5)
print('Server successfully started!')
app.add_task(notify_server_started_after_five_seconds())
You can check out Sanic docs for more details.
In one of my applications, I use this kind of background task to run an async function that checks for updates to certain configs in the Firestore database. You can see sample code for that task above. This task runs on server start, and stays in the background for the whole life of the application.
Wanted Solution
I am exploring migrating this application from Sanic to FastAPI, and would like the ability to run this kind of background task. It’s unfortunate that the term “background tasks” in FastAPI/Starlette becomes overloaded. FastAPI could call them ‘async tasks’ or something else.
I’m also not sure how this plays into FastAPI seemingly not having the concept of an application context (assuming that is still the case?)
Wanted Code
from fastapi import FastAPI
app = FastAPI()
# ... same async function as above
@app.on_event("startup")
async def startup_event():
app.add_task(poll_for_config_updates) # like in Sanic (the method could have another name)
Alternatives
Perhaps using Depends
as described here?
Operating System
Linux, macOS
Operating System Details
No response
FastAPI Version
0.72.0
Python Version
Python 3.9.7
Additional Context
No response
Issue Analytics
- State:
- Created 2 years ago
- Reactions:2
- Comments:5 (1 by maintainers)
Top GitHub Comments
Sanic does a bit more than just wrap
asyncio.create_task
: https://github.com/sanic-org/sanic/blob/ac388d644b1e22156e228470fad8ea34932c080a/sanic/app.py#L1197 For one, it makes sure that the tasks are only added to the loop after the application/loop starts. It then also handles the case where those tasks are delayed, if they were scheduled before the loop started.It also keeps track of those tasks in a registry, and cleans them up when the application shuts down.
That’s probably something that can be manually copied too, but it would be nice for that to be handled by the framework.
Yes, that’s the idea 🙂 Like with Sanic, it would be great if the application could keep track of and handle the cleanup of the async tasks instead of having to do it manually – although I do understand that for some cases that might not be too hard.
Sanic just wraps
asyncio.create_task
, anyway.https://github.com/sanic-org/sanic/blob/ac388d644b1e22156e228470fad8ea34932c080a/sanic/app.py#L1159