Registry / web-framework / fast-depends

fast-depends

JSON →
library3.0.8pypypi✓ verified 24d ago

FastDepends is a lightweight Python library providing a dependency injection system, extracted and refined from FastAPI's core logic. It allows developers to use FastAPI-like dependency resolution and type casting in any Python project, whether synchronous or asynchronous, without the HTTP-specific components. Currently at version 3.0.8, the library maintains an active development pace with frequent updates and bug fixes.

pip install fast-depends
INSTALL
IMPORT
SIG · FAST-DEPENDS
F
fast-depends
web-frameworkpythonv3.0.8
Install
2.9s avg
Import
354ms
Disk
28MB
Pass rate
10/ 10
Env Coverage10 / 10
glibc
3.93.13
musl
3.93.13
Install & Compatibility
Where this runs
tested against v3.0.8 · pip install
no network on importno background threads
Install × environment matrix
Each cell = how many times install + import succeeded across repeated harness runs. Partial = flaky.
glibc = Debian/Ubuntu slim · musl = Alpine Linux
musl
py 3.103.915 runs
installs and imports cleanly · install 0.0s · import 0.365s · 29.9MB
glibc
py 3.103.915 runs
installs and imports cleanly · install 2.9s · import 0.344s · 30MB
28MB installed
● package 28MB
Code
Verified usage

Verified import paths — ran on the pinned version, not inferred.

inject
from fast_depends import inject
The primary decorator for applying dependency injection to functions.
Depends
from fast_depends import Depends
Used to declare a dependency on another callable.
ContextDepends
from fast_depends import ContextDepends
Used for injecting context-aware dependencies (e.g., current request, user).
PydanticSerializer
from fast_depends.pydantic import PydanticSerializer
Required when explicitly using Pydantic for serialization/validation with @inject.
MsgSpecSerializer
from fast_depends.msgspec import MsgSpecSerializer
Required when explicitly using Msgspec for high-performance serialization/validation with @inject.

This quickstart demonstrates basic synchronous and asynchronous dependency injection using the `@inject` decorator and `Depends` for declaring dependencies. The `get_user_id` dependency is resolved and injected into `process_data`, while `async_get_greeting` is resolved into `greet_user`.

from fast_depends import inject, Depends def get_user_id() -> int: return 42 @inject def process_data(data: str, user_id: int = Depends(get_user_id)) -> str: return f"Processing '{data}' for user {user_id}" result = process_data("hello world") print(result) # Async example (requires an event loop) import asyncio async def async_get_greeting() -> str: await asyncio.sleep(0.1) return "Hello" @inject async def greet_user(name: str, greeting: str = Depends(async_get_greeting)) -> str: return f"{greeting}, {name}!" async def main_async(): async_result = await greet_user("Alice") print(async_result) # To run the async example in a synchronous environment: # asyncio.run(main_async())
Debug
Known issues
breakingVersion 3.0.0 introduced explicit serializer selection. If you were implicitly relying on Pydantic v1 behavior, you now need to explicitly pass a serializer instance (e.g., `PydanticSerializer()`) to the `@inject` decorator.
fix
Update `@inject` calls to specify `serializer=PydanticSerializer()` or `serializer=MsgSpecSerializer()` if custom validation or serialization fields (like `Pydantic.Field` or `Msgspec.field`) are used. For basic type casting, no explicit serializer might be needed.
affects: >=3.0.0
gotchaWhen running in a synchronous context, only synchronous dependencies are available. Asynchronous dependencies can only be resolved when the `@inject`'ed function itself is asynchronous and an event loop is running.
fix
Ensure that `async def` dependencies are only used within `async def` functions decorated with `@inject`, and that these functions are called within an active asyncio event loop. For synchronous `inject`'ed functions, use `def` dependencies.
affects: All
gotchaDependencies are cached by default within a single call to an `@inject`'ed function. This means if a dependency is called multiple times by different sub-dependencies within the same top-level `@inject` call, it will only execute once and return the cached result.
fix
If a dependency needs to be executed every time it's referenced (e.g., for side effects or fresh data), set `cache=False` when declaring it: `Depends(my_dependency, cache=False)`.
affects: All
gotchaFastDepends leverages Pydantic for validation and type casting by default. Mixing FastDepends with projects or dependencies that are strictly tied to Pydantic v1 might lead to compatibility issues, especially if the new explicit serializer system is not used correctly.
fix
Ensure consistent Pydantic versions across your project. When using Pydantic-specific features with FastDepends, explicitly use `fast_depends.pydantic.PydanticSerializer` and ensure your Pydantic model definitions align with the installed Pydantic version (v1 or v2). FastDepends v3.x is generally compatible with Pydantic v2.
affects: All (especially with Pydantic v1/v2 transition)
Errors
Common errors & fixes
ModuleNotFoundError: No module named 'fast_depends'
The `fast-depends` library has not been installed, or the Python environment where the code is being run does not have it installed or activated.
fix
Ensure the library is installed using pip: `pip install fast-depends`.
AttributeError: 'Depends' object has no attribute '...' (when trying to access an attribute of the Depends object directly)
This error occurs when you try to use `Depends()` directly as if it were the resolved dependency value, outside of a function decorated with `@inject` (or a FastAPI endpoint), where the dependency injection system would normally resolve it.
fix
Dependencies marked with `Depends` must be parameters of a function decorated with `@inject` for `fast-depends` to correctly resolve and inject the actual dependency value. Ensure the calling function is decorated and `Depends` is used as a default parameter value. 

```python
from fast_depends import inject, Depends

def get_config():
    return {'setting': 'value'}

@inject
def my_function(config: dict = Depends(get_config)):
    return config['setting'] # Correct usage

# Incorrect usage would be: 
# config_obj = Depends(get_config) 
# print(config_obj.setting) # This would raise the AttributeError
```
TypeError: 'coroutine' object is not callable (or similar errors related to async/sync mismatch)
This typically happens when an asynchronous dependency function is used in a synchronous context, or vice-versa, without proper handling by the `fast-depends` injector. While `fast-depends` supports both, issues can arise if the dependency's execution environment doesn't match its definition (e.g., calling an `async def` dependency from a `def` function that isn't itself part of an async `inject` chain).
fix
Ensure that if your dependency is `async def`, the function that consumes it (which is decorated with `@inject`) is also `async def` and is awaited when called. Similarly, if you have a synchronous `@inject` function, avoid using `async def` dependencies unless `fast-depends` can correctly manage the thread pool for it.

```python
import asyncio
from fast_depends import inject, Depends

async def async_dependency():
    await asyncio.sleep(0.1)
    return 42

# Correct: async inject function for async dependency
@inject
async def consumer_async(value: int = Depends(async_dependency)):
    return value

# Incorrect: sync inject function trying to consume async dependency directly without proper context
# @inject
# def consumer_sync(value: int = Depends(async_dependency)): 
#     return value

# To run an async inject function
result = asyncio.run(consumer_async())
```
Dependency functions are not executed / Dependency is not resolved (often leading to NoneType errors or incorrect values)
The `@inject` decorator, which is responsible for enabling `fast-depends` to resolve and inject dependencies, has been omitted or incorrectly applied to the function that declares dependencies. Without `@inject`, `Depends` objects are not processed.
fix
Always decorate the function where you declare `Depends` dependencies with `@inject`.

```python
from fast_depends import inject, Depends

def get_value():
    return 10

@inject # This decorator is crucial
def calculate(a: int, b: int = Depends(get_value)):
    return a + b

# Example of what happens without @inject (b would remain a Depends object, not 10)
# def calculate_wrong(a: int, b: int = Depends(get_value)):
#     return a + b
```
Upgrade
Version history
3.0.8latest on PyPI · released Mar 2, 2026
Audit
Dependencies
typing-extensionsrequiredRequired for older Python versions to support advanced type hints.
anyiorequiredUsed for asynchronous operations and compatibility.
pydanticoptionalOptional, for Pydantic-based validation and serialization (e.g., PydanticSerializer, Field).
msgspecoptionalOptional, for high-performance Msgspec-based serialization (e.g., MsgSpecSerializer, field).
Agent activity
10 hits · last 30 days
node
8
Amazon
1
Resources
fast-depends — pip install fast-depends · libregistry