databasetestingmockingdependenciesfastapi

FastAPI : dependency_overrides not overriding database session (pytest)


I'm reading the database testing with SQLmodel chapter and try to reproduce the testings with fixtures approach.

My code is identical with the provided examples, but for a reason, my test is unable to use the mocked session that I give. This is my code :

main.py

settings = Settings()
app = FastAPI()

app.add_middleware(CORSMiddleware, allow_origins=settings.allowed_origins, allow_credentials=True, allow_methods=["*"], allow_headers=["*"])

app.include_router(router)
add_pagination(app)

my endpoint

from database import get_session

@router.get("")
def get_lexicon_entry(id: int, session: Session = Depends(get_session)):

    lex = session.exec(select(lxmodel).where(lxmodel.id == id)).first()
    return lex

my test file (/tests)

from database import get_session

@pytest.fixture(name="session")
def session_fixture():
    print("session_fixture")
    engine = create_engine(
        "sqlite:///testing.db", connect_args={"check_same_thread": False}
    )
    SQLModel.metadata.create_all(engine)
    with Session(engine) as session:
        yield session


def test_get_lexicon_entry(session: Session):

    def get_session_override():
        return session

    app.dependency_overrides[get_session] = get_session_override
    client = TestClient(app)
    response = client.get("/lexicon/entry?id=50")
    assert response.status_code == 404
    app.dependency_overrides.clear()

database.py

# ...engine declaration details...

def get_session():
    with Session(engine) as session:
        yield session

The response has a 200 status, so, the assertion raises an error. When I print the response with print(response.json()) it shows an entry that is in my production db.

When I run the test, the testing db is created; and when I check the content of the db, it is empty. This seem to indicates that the dependency is not correctly override.

I'm I missing something ?

Thank you in advance.

FastAPI version : latest


Solution

  • The problem was coming from the routes param on the FastAPI class in the main.py file.

    app = FastAPI(
        title="title",
        description="API",
        version="0.2",
        servers=[{"url": "http://localhost:8000", "description": "Localhost"}],
        routes=router.routes, # don't use that !
    ...
    )
    

    When the param is removed, the dependencies are effectively overridden by the fixtures and tests can run with the appropriate session.

    I don't know if this a FastAPI issue.