# How to Use FastCRUD with Existing FastAPI Applications: A Complete Integration Guide

> Integrate FastCRUD into your existing FastAPI app. Learn how to generate async CRUD endpoints easily with the crud_router function and include it seamlessly.

- Repository: [Benav Labs/fastcrud](https://github.com/benavlabs/fastcrud)
- Tags: how-to-guide
- Published: 2026-02-26

---

**FastCRUD integrates with existing FastAPI applications by generating async CRUD endpoints through the `crud_router` function, which creates an `APIRouter` that can be directly included in your main FastAPI app using standard `include_router` patterns.**

The `benavlabs/fastcrud` library provides a thin abstraction layer that adds **async-ready, feature-rich CRUD operations** on top of SQLAlchemy 2.x (or SQLModel) models. By leveraging the `crud_router` builder and `EndpointCreator` classes, you can wire fully functional REST endpoints into existing FastAPI projects without refactoring your database layer or application structure.

## Understanding FastCRUD's Architecture

FastCRUD operates through three distinct layers that work together to generate endpoints while preserving your existing FastAPI setup.

### The Core CRUD Layer

The `FastCRUD` class in [[`fastcrud/crud/fast_crud.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/crud/fast_crud.py)](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/crud/fast_crud.py) provides generic methods including `create`, `get`, `get_multi`, `get_joined`, `update`, `delete`, `db_delete`, `upsert`, and `count`. This class handles advanced filtering, sorting, cursor-pagination, and multi-dialect upserts while remaining completely model-agnostic.

### The Router Builder

The [[`fastcrud/endpoint/crud_router.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/crud_router.py)](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/crud_router.py#L19-L84) file contains the `crud_router` convenience function (lines 19-84). This function instantiates `EndpointCreator` and returns a fully configured `APIRouter` that you can immediately include in your existing FastAPI application using `app.include_router()`.

### The Endpoint Creator

The [[`fastcrud/endpoint/endpoint_creator.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/endpoint_creator.py)](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/endpoint_creator.py#L62-L140) class implements the actual endpoint functions (`_create_item`, `_read_item`, `_read_items`, etc.) on lines 62-140. It handles dependency injection, automatic relationship inclusion, filter validation, and response-model conversion before registering routes with the router.

## Step-by-Step Integration Guide

Integrating FastCRUD into an existing FastAPI application requires four main steps: defining schemas, creating a session dependency, generating the router, and including it in your app.

### Define Your SQLAlchemy Models and Pydantic Schemas

FastCRUD requires SQLAlchemy 2.x declarative models (or SQLModel) and separate Pydantic schemas for create, update, and read operations.

```python

# app/models.py

from sqlalchemy import Column, Integer, String
from sqlalchemy.orm import DeclarativeBase

class Base(DeclarativeBase):
    pass

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

```

```python

# app/schemas.py

from pydantic import BaseModel

class ItemCreateSchema(BaseModel):
    name: str
    description: str | None = None

class ItemReadSchema(BaseModel):
    id: int
    name: str
    description: str | None = None

```

### Create an Async Session Dependency

FastCRUD expects a callable that returns an `AsyncSession`, typically wrapped in FastAPI's `Depends`.

```python

# app/database.py

from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine, async_sessionmaker
from typing import AsyncGenerator

DATABASE_URL = "sqlite+aiosqlite:///./test.db"
engine = create_async_engine(DATABASE_URL, echo=False)
AsyncSessionLocal = async_sessionmaker(engine, class_=AsyncSession, expire_on_commit=False)

async def get_session() -> AsyncGenerator[AsyncSession, None]:
    async with AsyncSessionLocal() as session:
        yield session

```

### Generate the CRUD Router

Use the `crud_router` function to create an `APIRouter` instance configured for your model.

```python

# app/main.py

from fastapi import FastAPI
from fastcrud import crud_router
from .database import get_session, engine
from .models import Base, Item
from .schemas import ItemCreateSchema, ItemReadSchema

app = FastAPI()

@app.on_event("startup")
async def init_db():
    async with engine.begin() as conn:
        await conn.run_sync(Base.metadata.create_all)

item_router = crud_router(
    session=get_session,
    model=Item,
    create_schema=ItemCreateSchema,
    update_schema=ItemCreateSchema,
    select_schema=ItemReadSchema,
    path="/items",
    tags=["Items"],
)

app.include_router(item_router)

```

The `crud_router` function (lines 19-84 in [`fastcrud/endpoint/crud_router.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/crud_router.py)) instantiates `EndpointCreator` and returns a router that implements `POST /`, `GET /{pk}`, `GET /`, `PATCH /{pk}`, and `DELETE /{pk}` endpoints.

## Advanced Integration Patterns

Once basic integration is working, you can customize the generated endpoints to fit your existing application's requirements.

### Adding Authentication Dependencies

Inject custom dependencies into specific CRUD operations using the `read_deps`, `create_deps`, `update_deps`, and `delete_deps` parameters.

```python
from fastapi import Depends, HTTPException, status
from .deps import get_current_user

item_router = crud_router(
    session=get_session,
    model=Item,
    create_schema=ItemCreateSchema,
    update_schema=ItemCreateSchema,
    select_schema=ItemReadSchema,
    path="/items",
    tags=["Items"],
    read_deps=[get_current_user],
    update_deps=[get_current_user],
    delete_deps=[get_current_user],
)

```

The `EndpointCreator.add_routes_to_router` method (lines 77-84 in [`fastcrud/endpoint/endpoint_creator.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/endpoint_creator.py)) receives these dependency lists and passes them to FastAPI's `router.add_api_route` via the `inject_dependencies` utility.

### Enabling Automatic Relationship Joins

FastCRUD can automatically detect and join SQLAlchemy relationships, returning nested data structures in your API responses.

```python

# models.py

from sqlalchemy import Column, Integer, String, ForeignKey
from sqlalchemy.orm import relationship

class Category(Base):
    __tablename__ = "categories"
    id = Column(Integer, primary_key=True)
    name = Column(String)

class Item(Base):
    __tablename__ = "items"
    id = Column(Integer, primary_key=True)
    name = Column(String)
    category_id = Column(Integer, ForeignKey("categories.id"))
    category = relationship("Category", backref="items")

```

```python

# schemas.py

class CategoryReadSchema(BaseModel):
    id: int
    name: str

class ItemReadSchema(BaseModel):
    id: int
    name: str
    category: CategoryReadSchema | None = None

```

```python

# main.py

item_router = crud_router(
    session=get_session,
    model=Item,
    create_schema=ItemCreateSchema,
    update_schema=ItemCreateSchema,
    select_schema=ItemReadSchema,
    path="/items",
    tags=["Items"],
    include_relationships=True,
    nest_joins=True,
)

```

The join configuration logic resides in `EndpointCreator._get_join_params` (lines 61-84 in [`fastcrud/endpoint/endpoint_creator.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/endpoint_creator.py)), which builds the parameters for `FastCRUD.get_multi_joined` and `get_joined` calls.

### Custom Endpoints with EndpointCreator

For complex business logic that extends beyond standard CRUD, use `EndpointCreator` directly to mix auto-generated and custom routes.

```python
from fastcrud import EndpointCreator
from fastapi import APIRouter, Depends
from sqlalchemy import select, func

custom_creator = EndpointCreator(
    session=get_session,
    model=Item,
    create_schema=ItemCreateSchema,
    update_schema=ItemCreateSchema,
    select_schema=ItemReadSchema,
)

async def price_summary(
    category_id: int | None = None,
    db: AsyncSession = Depends(get_session),
):
    query = select(func.sum(Item.price))
    if category_id is not None:
        query = query.where(Item.category_id == category_id)
    result = await db.execute(query)
    total = result.scalar_one_or_none() or 0
    return {"total_price": float(total)}

# Add standard CRUD routes

custom_creator.add_routes_to_router()

# Add custom business logic endpoint

custom_creator.add_custom_route(
    endpoint=price_summary,
    methods=["GET"],
    path="/price-summary",
    tags=["Analytics"],
    summary="Total price of items (optional filter by category)",
)

app.include_router(custom_creator.router, prefix="/items")

```

The `add_custom_route` method (lines 71-84 in [`fastcrud/endpoint/endpoint_creator.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/endpoint_creator.py)) forwards to FastAPI's `router.add_api_route`, allowing seamless integration of custom handlers alongside library-generated endpoints.

## Summary

- **FastCRUD** provides a model-agnostic CRUD layer in [`fastcrud/crud/fast_crud.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/crud/fast_crud.py) with async operations, advanced filtering, and relationship joining.
- The **`crud_router`** function in [`fastcrud/endpoint/crud_router.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/crud_router.py) generates a complete `APIRouter` that plugs into existing FastAPI applications via `app.include_router()`.
- **`EndpointCreator`** in [`fastcrud/endpoint/endpoint_creator.py`](https://github.com/benavlabs/fastcrud/blob/main/fastcrud/endpoint/endpoint_creator.py) handles endpoint implementation, dependency injection, and custom route registration.
- Integration requires only four steps: define schemas, create an async session dependency, call `crud_router`, and include the resulting router.
- Advanced features include per-endpoint authentication dependencies, automatic SQLAlchemy relationship joining, and custom endpoint mixing through direct `EndpointCreator` usage.

## Frequently Asked Questions

### Can I use FastCRUD with an existing SQLAlchemy database setup?

Yes. FastCRUD is designed to work with existing SQLAlchemy 2.x declarative models and database engines. You do not need to modify your table definitions or migration scripts. Simply pass your existing model class to the `crud_router` function along with your current async session dependency, and FastCRUD will inspect the model metadata to generate appropriate endpoints.

### How do I add authentication to specific CRUD endpoints?

Use the dependency injection parameters in `crud_router` or `EndpointCreator`. Pass a list of dependency callables to `read_deps`, `create_deps`, `update_deps`, or `delete_deps` to secure specific operations. These dependencies are forwarded to FastAPI's `router.add_api_route` via the `inject_dependencies` utility in `EndpointCreator.add_routes_to_router` (lines 77-84), ensuring standard FastAPI dependency resolution.

### Does FastCRUD support automatic joining of related tables?

Yes. Set `include_relationships=True` when calling `crud_router` to enable automatic detection of SQLAlchemy relationships. Use `nest_joins=True` to return nested JSON structures rather than flat column results. The join configuration logic resides in `EndpointCreator._get_join_params` (lines 61-84), which builds parameters for `FastCRUD.get_multi_joined` and `get_joined` methods to handle the actual database queries.

### Can I mix auto-generated CRUD routes with custom business logic endpoints?

Absolutely. Instantiate `EndpointCreator` directly instead of using the `crud_router` convenience function. Call `add_routes_to_router()` to register standard CRUD endpoints, then use `add_custom_route()` (lines 71-84 in [`endpoint_creator.py`](https://github.com/benavlabs/fastcrud/blob/main/endpoint_creator.py)) to register bespoke endpoints that mix CRUD operations with custom business logic. Finally, include the `EndpointCreator.router` in your FastAPI app using `app.include_router()`.