Search code examples
pythonfastapistarlette

FastAPI - How can I modify request from inside dependency?


How can I modify request from inside a dependency? Basically I would like to add some information (test_value) to the request and later be able to get it from the view function (in my case root() function).

Below is a simple example:

from fastapi import FastAPI, Depends, Request

app = FastAPI()

def test(request: Request):
    request['test_value'] = 'test value'

@app.get("/", dependencies=[Depends(test)])
async def root(request: Request):
    print(request.test_value)
    return {"test": "test root path."}

Solution

  • Option 1

    You could store arbitrary extra state to request.state, and use the Request object inside the endpoint to retrieve the state (the relevant implementation of Starlette's State method and class can be found here and here, respectively):

    from fastapi import FastAPI, Depends, Request
    
    app = FastAPI()
    
    def func(request: Request):
        request.state.test = 'test value'
    
    @app.get('/', dependencies=[Depends(func)])
    def root(request: Request):
        return request.state.test
    

    If you would like that state (i.e., test attribute above) to be globally accessible from any request/user, you might want to store it on the application instance, as described in this answer, as well this and this answer.

    Option 2

    Instead of adding dependencies=[Depends(test)] to the decorator of the endpoint, you could use the dependency injection directly, by defining test (in this example) as an endpoint parameter and using Depends. You could then have the dependency function returning the attribute. Using this option, however, you would have to do this for every endpoint in your app/router, if you had to define a global dependency for the entire app/router, as demonstrated here and here.

    from fastapi import FastAPI, Depends, Request
    
    app = FastAPI()
    
    def func(request: Request):
        return 'test value'
    
    @app.get('/')
    def root(request: Request, test: str = Depends(func)):
        return test