dipin
dipin provides a dependency injection container, that primarily aims to work well with FastAPI.
Motivation
FastAPI's dependency container works well, but can be messy to scale. Out of
the box, you can end up with many Annotated[X, Depends()]. Some projects I've
worked on have a sprawling di.py, and references to Depends in non-FastAPI code.
dipin aims to:
- Remove the need to annotate types in non-FastAPI code with
Depends, - Provide a simple API to access dependencies in route-handlers, e.g.:
from dipin import DI @app.get("/") async def homepage(request: Request, user: DI[AuthenticatedUser]): ...
vsfrom .auth import get_authenticated_user @app.get("/") async def homepage(request: Request, user: Annotated[User, Depends(get_authenticated_user)]): ...
Architecture
TODO
Usage (alpha, buggy, will change)
# di.py
from dipin import DI
# Register a singleton across all requests
from .settings import Settings # e.g. a pydantic-settings model
DI.register_instance(Settings())
# Register a factory (lazy singleton), called once across all requests
from sqlalchemy.ext.asyncio import create_async_engine
from sqlalchemy.ext.asyncio.engine import AsyncEngine
def create_engine(settings: DI[Settings]) -> AsyncEngine:
return create_async_engine(str(settings.database_dsn))
DI.register_factory(AsyncEngine, get_db_engine, create_once=True)
# Register a factory called per-request
from sqlmodel.ext.asyncio.session import AsyncSession
from sqlalchemy.ext.asyncio import async_sessionmaker
async def create_session(engine: DI[AsyncEngine]) -> AsyncSession:
sessionmaker = async_sessionmaker(
bind=engine, class_=AsyncSession, expire_on_commit=False
)
async with sessionmaker() as session:
yield session
DI.register_factory(AsyncSession, create_session)
# app.py
from fastapi import FastAPI
from sqlmodel.ext.asyncio.session import AsyncSession
from dipin import DI
app = FastAPI()
@app.get("/")
async def list_orders(session: DI[AsyncSession]):
qry = "SELECT * FROM orders"
res = await session.exec(qry)
orders = res.all()
return {"orders": orders}
Roadmap
- Support default arguments in factories
- e.g.
class A: def __init__(self, foo: str = "bar")should be instantiable.
- e.g.
- Named dependencies
- e.g.
DI["PrivateOpenAIClient"] - Out of the box, it seems to lookup the class name (as a deferred annotation), but
typing.Literalsupports this.
- e.g.
- Full typing support
- Currently
DI[Class]does not resolve to an instance ofClass.
- Currently
- Support many types of dependencies
- Including named (but we won't be able to use
DI[...]), and some of those described in python-dependency-injector. - Providing our own
fastapi.Dependsis likely needed.
- Including named (but we won't be able to use
Metadata
Release files for dipin 0.0.3
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | |
|---|---|---|---|---|
| dipin-0.0.3.tar.gz | 9.8 kB | Without provenance | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| dipin-0.0.3-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 17.4 kB
Release files / dipin-0.0.3.tar.gz
| Download URL | dipin-0.0.3.tar.gz |
|---|---|
| Size | 9.8 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
85e0bc8ec7b509aa43ad53457543fb056e524d26fd290ade633f9067d7741578
|
|
BLAKE2b-256 checksum How to use checksums |
99d1e939eef6dd59033073191320c3cfed6a8b41da83ea359d579d1e56d1f802
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/5.0.0 CPython/3.12.4
|
Release files / dipin-0.0.3-py3-none-any.whl
| Download URL | dipin-0.0.3-py3-none-any.whl |
|---|---|
| Size | 7.6 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
97c23d7b4cdd5eb2fcb34ee29313dfe9006018bc2a9a42b3ddb17136ed9f7236
|
|
BLAKE2b-256 checksum How to use checksums |
78eaee76432367d9432bcb997f26da1fcd07aa6f2bdb9d7a0619133c2350c087
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/5.0.0 CPython/3.12.4
|
Security for dipin 0.0.3
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.