Skip to main content

Class-based views for FastAPI routers — a maintained, FastAPI 0.137+ compatible drop-in for fastapi_utils.cbv.

Project description

fastapi-cbv-router

CI PyPI version Python versions License: MIT

Class-based views (CBV) for FastAPI routers — a small, maintained drop-in replacement for the unmaintained fastapi_utils.cbv. Works on modern FastAPI (tested from 0.115), and in particular survives FastAPI 0.137+, where fastapi_utils.cbv breaks.

Why

fastapi_utils.cbv relied on APIRouter.include_router eagerly copying APIRoute objects into router.routes. FastAPI 0.137 made include_router lazy, which broke fastapi_utils whenever two @cbv decorators shared one router.

fastapi-cbv-router rebuilds each endpoint through the router's public add_api_route / add_api_websocket_route API, which stays eager and delegates all route-state computation back to FastAPI. Route configuration is copied by introspecting add_api_route's own parameters, so the package adapts to upstream FastAPI changes instead of hard-coding a kwarg list.

Features

  • One small decorator, @cbv(router) — no base classes or metaclasses required.
  • Share a single dependency instance (self) across every endpoint on a class.
  • Inject dependencies either as class-level annotated attributes or through a custom __init__ — use whichever fits your style.
  • Works with regular HTTP routes and WebSocket routes.
  • Preserves all route configuration (status_code, response_model, dependencies, tags, …) and the router prefix.
  • Fully typed (py.typed), zero dependencies beyond FastAPI.

Requirements

  • Python: 3.13+
  • FastAPI: 0.115+ — continuously tested against the latest release, currently 0.137.2. The test suite specifically covers FastAPI 0.137+, where include_router became lazy and broke fastapi_utils.cbv.

Install

pip install fastapi-cbv-router
# or
uv add fastapi-cbv-router

Quickstart

from fastapi import APIRouter, Depends, FastAPI
from fastapi_cbv_router import cbv

router = APIRouter(prefix="/items")


def get_db() -> str:
    return "db-connection"


@cbv(router)
class ItemsView:
    db: str = Depends(get_db)

    @router.get("/")
    def list_items(self) -> dict:
        return {"db": self.db, "items": []}

    @router.post("/")
    def create_item(self, name: str) -> dict:
        return {"db": self.db, "created": name}


app = FastAPI()
app.include_router(router)

Class-level annotated attributes become keyword-only dependencies injected via Depends(ItemsView) and are available as self.<attr> in every endpoint. ClassVar-annotated attributes are treated as plain class constants and are not injected.

Dependency injection via __init__

If you prefer constructor injection — for example to keep a clean abstract base and wire dependencies explicitly — define a custom __init__. Its parameters are resolved by FastAPI when the view is constructed, exactly like an endpoint's parameters:

import abc
from http import HTTPStatus

from fastapi import APIRouter, Depends
from fastapi_cbv_router import cbv

router = APIRouter(prefix="/items", tags=["items"])


def get_service() -> "ItemService":
    ...


class ItemApi(abc.ABC):
    @abc.abstractmethod
    async def get_item(self, item_id: int) -> dict: ...


@cbv(router)
class HttpItemApi(ItemApi):
    def __init__(self, service: "ItemService" = Depends(get_service)) -> None:
        self.service = service

    @router.get("/{item_id}", status_code=HTTPStatus.OK)
    async def get_item(self, item_id: int) -> dict:
        return await self.service.fetch(item_id)

This pairs cleanly with DI containers such as dependency-injector: use Depends(Provide[...]) defaults on the @inject-decorated __init__.

WebSocket routes

WebSocket endpoints are supported the same way as HTTP routes:

from fastapi import APIRouter, WebSocket
from fastapi_cbv_router import cbv

router = APIRouter()


@cbv(router)
class ChatView:
    @router.websocket("/ws")
    async def chat(self, websocket: WebSocket) -> None:
        await websocket.accept()
        await websocket.send_text("hello")
        await websocket.close()

Scope

Only the plain @cbv(router) form is supported (no *urls / set_responses helpers). This is intentional — it covers the common case with the smallest, most maintainable surface.

License

MIT

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

fastapi_cbv_router-0.1.0.tar.gz (6.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

fastapi_cbv_router-0.1.0-py3-none-any.whl (6.9 kB view details)

Uploaded Python 3

File details

Details for the file fastapi_cbv_router-0.1.0.tar.gz.

File metadata

  • Download URL: fastapi_cbv_router-0.1.0.tar.gz
  • Upload date:
  • Size: 6.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.11.22 {"installer":{"name":"uv","version":"0.11.22","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for fastapi_cbv_router-0.1.0.tar.gz
Algorithm Hash digest
SHA256 cc1b2e6a4a5cdbb9236cb146cc54feb4d234757928fe3a46c46e7bc46ca45a1c
MD5 9a62510a2ef2957f2bf8a5b60836a05f
BLAKE2b-256 78a451e4abbaf11f711d42da194ae74dfc5ff27068ee26f3cc2a1acacf54569b

See more details on using hashes here.

File details

Details for the file fastapi_cbv_router-0.1.0-py3-none-any.whl.

File metadata

  • Download URL: fastapi_cbv_router-0.1.0-py3-none-any.whl
  • Upload date:
  • Size: 6.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.11.22 {"installer":{"name":"uv","version":"0.11.22","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for fastapi_cbv_router-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 1600f8a6d7eca9d5a62c186ea90bc2e4195e00abc6cbf70084e4777adc5ed343
MD5 c71b4e78ca0299387d1e3c4f7145a2bc
BLAKE2b-256 15fc691db01206e65d7bca33f52cd273d7d33727e3d9b7f0405cd59ca5dd17e8

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page