0
0
FastAPIframework~5 mins

Testing with database in FastAPI

Choose your learning style9 modes available
Introduction

Testing with a database helps make sure your app works well when saving or reading data. It checks if your database code is correct and reliable.

When you want to check if your app saves user info correctly.
When you need to verify that data updates happen as expected.
When you want to test queries that fetch data from the database.
When you want to catch errors before your app goes live.
When you want to run automated tests that include database actions.
Syntax
FastAPI
from fastapi.testclient import TestClient
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
from myapp.main import app, get_db
from myapp.database import Base

# Create a test database engine
SQLALCHEMY_DATABASE_URL = "sqlite:///./test.db"
engine = create_engine(SQLALCHEMY_DATABASE_URL, connect_args={"check_same_thread": False})
TestingSessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)

# Override the get_db dependency to use test DB
def override_get_db():
    db = TestingSessionLocal()
    try:
        yield db
    finally:
        db.close()

app.dependency_overrides[get_db] = override_get_db

client = TestClient(app)

Use a separate test database to avoid messing with real data.

Override the database dependency in FastAPI to use the test database during tests.

Examples
This test sends a POST request to create an item and checks if it was created correctly.
FastAPI
def test_create_item():
    response = client.post("/items/", json={"name": "Test Item"})
    assert response.status_code == 200
    assert response.json()["name"] == "Test Item"
This test fetches all items and checks if the response is a list.
FastAPI
def test_read_items():
    response = client.get("/items/")
    assert response.status_code == 200
    assert isinstance(response.json(), list)
Sample Program

This example shows a FastAPI app with a simple Item model and a POST endpoint to create items. It sets up a separate test database and overrides the database dependency for testing. The test sends a request to create an item and checks the response.

FastAPI
from fastapi import FastAPI, Depends
from fastapi.testclient import TestClient
from sqlalchemy import create_engine, Column, Integer, String
from sqlalchemy.orm import sessionmaker, declarative_base, Session

SQLALCHEMY_DATABASE_URL = "sqlite:///./test.db"
engine = create_engine(SQLALCHEMY_DATABASE_URL, connect_args={"check_same_thread": False})
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
Base = declarative_base()

class Item(Base):
    __tablename__ = "items"
    id = Column(Integer, primary_key=True, index=True)
    name = Column(String, index=True)

Base.metadata.create_all(bind=engine)

app = FastAPI()

def get_db():
    db = SessionLocal()
    try:
        yield db
    finally:
        db.close()

@app.post("/items/")
def create_item(name: str, db: Session = Depends(get_db)):
    item = Item(name=name)
    db.add(item)
    db.commit()
    db.refresh(item)
    return {"id": item.id, "name": item.name}

# Testing setup
SQLALCHEMY_TEST_DATABASE_URL = "sqlite:///./test_test.db"
test_engine = create_engine(SQLALCHEMY_TEST_DATABASE_URL, connect_args={"check_same_thread": False})
TestingSessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=test_engine)
Base.metadata.create_all(bind=test_engine)

def override_get_db():
    db = TestingSessionLocal()
    try:
        yield db
    finally:
        db.close()

app.dependency_overrides[get_db] = override_get_db

client = TestClient(app)

def test_create_item():
    response = client.post("/items/", json={"name": "Test Item"})
    assert response.status_code == 200
    data = response.json()
    assert data["name"] == "Test Item"
    assert "id" in data

if __name__ == "__main__":
    test_create_item()
    print("Test passed")
OutputSuccess
Important Notes

Always use a separate database for tests to keep your real data safe.

Use FastAPI's dependency override feature to swap the database during tests.

Run tests often to catch bugs early.

Summary

Testing with a database helps verify your app's data handling.

Use a separate test database and override dependencies in FastAPI.

Write simple tests to check creating and reading data.