FastAPI - How to get app instance inside a router?
Asked Answered
R

1

14

I want to get the app instance in my router file, what should I do ?

My main.py is as follows:

# ...
app = FastAPI()
app.machine_learning_model = joblib.load(some_path)
app.include_router(some_router)
# ...

Now I want to use app.machine_learning_model in some_router's file , what should I do ?

Rating answered 28/2, 2022 at 16:33 Comment(0)
D
26

Since FastAPI is actually Starlette underneath, you could store the model on the app instance using the generic app.state attribute, as described in Starlette's documentation (see State class implementation too). Example:

app.state.ml_model = joblib.load(some_path)

As for accessing the app instance (and subsequently, the model) from outside the main file, you can use the Request object. As per Starlette's documentation, where a request is available (i.e., endpoints and middleware), the app is available on request.app. Example:

from fastapi import Request

@router.get('/')
def some_router_function(request: Request):
    model = request.app.state.ml_model
Dorchester answered 28/2, 2022 at 17:42 Comment(6)
May I add other request params in some_router_function ?Rating
Yes. You can define params as usual.Dorchester
Thank you for your answer! I'm quite shocked that FastAPI does not provide any streamlined possibility to store Singletons for the service lifecycle.Acadia
Does this load model into memory only once and then pass the reference? I assume there is, since there is only one instance of the app running in the process?Econah
@Econah It does, and it would be best to initialise that variable inside a startup/lifespan event hanlder, as described here. If you plan on having multiple workers active at the same time, you might want to have a look at this and this as well.Dorchester
Is it possible to define router-specific state? Suppose I have multiple routers, one per model; can I avoid loading them all in the top-level app's startup hook?Carabin

© 2022 - 2024 — McMap. All rights reserved.