Atomic-like Agnostic Object Storage Framework, the Pydantic way
Project description
Atomic-like Agnostic Object Storage Framework, the Pydantic way
Documentation: 📖 Docs
FennFlow is a Python s3 framework designed to help you quickly, confidently, and painlessly manipulate files in your object storage implementing SSOT pattern and Saga compensation flow.
Why use FennFlow?
Working with aiobotocore often feels like handling raw bytes and dicts. FennFlow wraps S3 operations into a high-level
Unit of Work pattern, providing:
- SSOT — the backend is the single source of truth for your file storage. No matter what your file storage contains, the backend ensures a consistent view of what exists.
- Saga compensation flow — if something fails mid-operation, all previous actions are automatically compensated in reverse order, leaving storage in a consistent state.
- Clean Architecture — treat S3 as proper repositories using mixins (
PutRepository,GetRepository, etc.). - Pydantic-powered models — work with
TextContent,JsonContent,ImageContentand others instead of raw bytes. - Testability — swap S3ConnectorConfig for InMemoryConnectorConfig and point the backend at an in-memory SQLite database. Zero infrastructure, zero mocks.
Supported Connectors
| Connector | Description | Documentation |
|---|---|---|
| AWS S3 (default) | s3 compatible object storage via aiobotocore | 📖 Docs |
| In-Memory | great for and tests and development | 📖 Docs |
Supported Backends
FennFlow uses backend as a source of truth for your file storage. No matter what your file storage contains, backend ensures your data is consistent.
| Backend | Description | Documentation |
|---|---|---|
| SQLAlchemy (default) | persistent metadata backend, great for all environments | 📖 Docs |
| In-Memory | great for and tests, development | 📖 Docs |
Backend Comparison
| Raw aiobotocore | SQLAlchemy (default) | |
|---|---|---|
| Consistency | 🔴 None No link between files and metadata |
✅ High Persistent across restarts |
| Compensation | 🔴 None Orphaned files on failure |
✅ High Automatic within session |
| Reliability | 🔴 Low Failures leave storage in unknown state |
✅ High Consistent state guaranteed across restarts |
| Latency | ✅ Lowest Pure S3 network overhead only |
🟡 Low/middle DB overhead |
| Infrastructure | ✅ None | ✅ None SQLite by default |
| Memory usage | ✅ None | ✅ Minimal Metadata persisted to disk, not held in-process |
Quick Start
Here's a minimal example of FennFlow:
import asyncio
from fennflow import ConfigDict, UnitOfWork
from fennflow.backends import SqlalchemyBackendConfig
from fennflow.connectors import S3ConnectorConfig
from fennflow.files import BinaryContent, JsonContent, MediaType, TextContent
from fennflow.repositories import (
DeleteRepository,
GetRepository,
ListRepository,
PutRepository,
S3RepoField,
)
# 1. Define your repository with mixins
class CrudRepository(
PutRepository,
DeleteRepository,
GetRepository,
ListRepository,
):
pass
# 2. Set up your Unit of Work
class UOW(UnitOfWork):
my_files = S3RepoField(CrudRepository, bucket_name="my_files")
config = ConfigDict(
backend=SqlalchemyBackendConfig(),
connector=S3ConnectorConfig(),
)
async def main():
text_file = TextContent.from_content("Hello, world!")
json_file = JsonContent.from_content([1, 2, 3])
from_path_binary_file = BinaryContent.from_local_path("my_file.txt")
binary_file = BinaryContent(data=b"some bytes", media_type=MediaType.TEXT_PLAIN)
async with UOW() as uow:
await uow.my_files.at("folder1").put(
text_file,
json_file,
from_path_binary_file,
binary_file,
)
paths = await uow.my_files.at("folder1").list()
print(paths) # ListResponse[Filepath, ...]
files = await uow.my_files.get(*paths)
print(files) # MediaResponse[TextContent, JsonContent, TextContent, BaseBinary]
if __name__ == "__main__":
asyncio.run(main())
(This example is complete, it can be run “as is”, assuming you’ve installed the fennflow package)
Next Steps
To try FennFlow for yourself, clone it and follow the instructions in the examples.
Read the docs to learn more about working with FennFlow.
Read the API Reference to understand FennFlow’s interface.
Learn how to utilize llms with FennFlow.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file fennflow-0.6.0.tar.gz.
File metadata
- Download URL: fennflow-0.6.0.tar.gz
- Upload date:
- Size: 247.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
022fedaf9a8178c6990e54b80d0867e535b3bd1f84d3c7532db49bd440d0ae24
|
|
| MD5 |
0a5b8b458d29e8eb569f3ce3cd344614
|
|
| BLAKE2b-256 |
802679a79fec1dcb0d25d74e9934f2f5540ce283d4b95d15a95b47f596b4d011
|
Provenance
The following attestation bundles were made for fennflow-0.6.0.tar.gz:
Publisher:
publish.yml on Alex-FIR-IT/FennFlow
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
fennflow-0.6.0.tar.gz -
Subject digest:
022fedaf9a8178c6990e54b80d0867e535b3bd1f84d3c7532db49bd440d0ae24 - Sigstore transparency entry: 1675576946
- Sigstore integration time:
-
Permalink:
Alex-FIR-IT/FennFlow@a73561e95aeed73b6a0a43870d3c9ff2ce759330 -
Branch / Tag:
refs/tags/v0.6.0 - Owner: https://github.com/Alex-FIR-IT
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@a73561e95aeed73b6a0a43870d3c9ff2ce759330 -
Trigger Event:
push
-
Statement type:
File details
Details for the file fennflow-0.6.0-py3-none-any.whl.
File metadata
- Download URL: fennflow-0.6.0-py3-none-any.whl
- Upload date:
- Size: 111.7 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
042505291382217138ff33b57e2ff0fca99ae9605ebfedddcc56520256b0a96c
|
|
| MD5 |
fda6f43c30509997c3a2061262bfbe09
|
|
| BLAKE2b-256 |
7d78cb69cd32d839662c0d39796b1ea6dff64f44d5e9f9512f10048c6049c9bb
|
Provenance
The following attestation bundles were made for fennflow-0.6.0-py3-none-any.whl:
Publisher:
publish.yml on Alex-FIR-IT/FennFlow
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
fennflow-0.6.0-py3-none-any.whl -
Subject digest:
042505291382217138ff33b57e2ff0fca99ae9605ebfedddcc56520256b0a96c - Sigstore transparency entry: 1675576970
- Sigstore integration time:
-
Permalink:
Alex-FIR-IT/FennFlow@a73561e95aeed73b6a0a43870d3c9ff2ce759330 -
Branch / Tag:
refs/tags/v0.6.0 - Owner: https://github.com/Alex-FIR-IT
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@a73561e95aeed73b6a0a43870d3c9ff2ce759330 -
Trigger Event:
push
-
Statement type: