Skuf
Minimal Dependency Injection & Configuration Framework for Python
🚀 Features
- ⚡️ Lightweight and zero-dependency
- 🧩 Simple Dependency Injection container
- 🔄 Context Manager support for Unit of Work patterns
- ⚡️ Async Context Manager support
- 🔐 Type-safe
.env-based configuration loader (likepydantic.BaseSettings) - 🧱 Suitable for scripts, CLI tools, microservices
📦 Installation
pip install skuf
🧰 Dependency Injection
from skuf import Dependency
# Define a Logger
class Logger:
def log(self, msg: str):
print(msg)
# Register the class
Dependency.register(Logger)
# Use with decorator for automatic injection
@Dependency.inject
def test_func(logger: Dependency[Logger]):
logger.log("Hello, World! From a function!")
# Or resolve manually
logger = Dependency.resolve(Logger)
logger.log("Hello, World!")
test_func()
# Output:
# Hello, World!
# Hello, World! From a function!
🔄 Unit of Work with Automatic Context Management
from skuf import Dependency
# Define a Unit of Work with context manager
class UnitOfWork:
def __init__(self):
self.operations = []
def add_operation(self, op: str):
self.operations.append(op)
def __enter__(self):
print("🚀 Starting transaction...")
return self
def __exit__(self, exc_type, exc_val, exc_tb):
if exc_type is None:
print(f"✅ Committing: {self.operations}")
else:
print(f"❌ Rolling back: {self.operations}")
# Register context manager
def create_uow():
return UnitOfWork()
Dependency.register(UnitOfWork, factory=create_uow)
# Use with automatic context management (like FastAPI)
@Dependency.inject
def business_logic(uow: Dependency[UnitOfWork]):
uow.add_operation("Create user")
uow.add_operation("Send email")
# Context automatically managed by decorator
business_logic() # Auto-commit on success, rollback on exception
⚡ Async Unit of Work
import asyncio
from skuf import Dependency
class AsyncUnitOfWork:
def __init__(self):
self.operations = []
def add_operation(self, op: str):
self.operations.append(op)
async def __aenter__(self):
print("🚀 Starting async transaction...")
return self
async def __aexit__(self, exc_type, exc_val, exc_tb):
if exc_type is None:
print(f"✅ Committing async: {self.operations}")
else:
print(f"❌ Rolling back async: {self.operations}")
# Register async context manager
def create_async_uow():
return AsyncUnitOfWork()
Dependency.register(AsyncUnitOfWork, async_context_manager=create_async_uow)
# Use in async business logic
@Dependency.inject
async def async_business_logic(uow: Dependency[AsyncUnitOfWork]):
uow.add_operation("Async create user")
uow.add_operation("Async send email")
# Context automatically managed by decorator
asyncio.run(async_business_logic())
🔄 Async Generator UoW with @asynccontextmanager
import asyncio
from contextlib import asynccontextmanager
from typing import AsyncGenerator
from skuf import Dependency
class IUnitOfWork:
def __init__(self):
self.operations = []
def add_operation(self, op: str):
self.operations.append(op)
@asynccontextmanager
async def get_uow() -> AsyncGenerator[IUnitOfWork, None]:
logger.debug('🚀 UnitOfWork started')
uow = IUnitOfWork()
try:
yield uow
logger.debug('✅ UnitOfWork completed successfully')
except Exception as e:
logger.error(f'❌ UnitOfWork failed: {e}')
raise
# Register async generator factory
Dependency.register(IUnitOfWork, async_generator_factory=get_uow)
# Use in business logic
@Dependency.inject
async def business_logic(uow: Dependency[IUnitOfWork]):
uow.add_operation("Create user")
uow.add_operation("Send email")
# Context automatically managed by decorator
asyncio.run(business_logic())
⚙️ Environment Settings
# .env
API_KEY=supersecret
TIMEOUT=5
DEBUG=true
RETRIES=3
ADMINS=123,456
# settings.py
from skuf import BaseSettings
from typing import List
class Settings(BaseSettings):
api_key: str
timeout: int
debug: bool
retries: int
admins: List[int]
settings = Settings()
print(settings.api_key) # supersecret
print(settings.timeout) # 5
print(settings.debug) # True
print(settings.admins) # [123, 456]
✅ Supports types:
- str, int, float, bool
- List[str], List[int], List[float] (via comma-separated values like A,B,C)
Metadata
Release files for skuf 0.3.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| skuf-0.3.0.tar.gz | 17.4 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| skuf-0.3.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 29.2 kB
Release files / skuf-0.3.0.tar.gz
| Download URL | skuf-0.3.0.tar.gz |
|---|---|
| Size | 17.4 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
0ca669b6b8824ff1f6ec35f9d245d5bd25076d69c3624f0c15dfa6e9e08447b4
|
|
BLAKE2b-256 checksum How to use checksums |
d2b694ee0e2542f14b459b43ae02fd280a766439abdfda7972cc113ac9ee142f
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.9.5
|
Release files / skuf-0.3.0-py3-none-any.whl
| Download URL | skuf-0.3.0-py3-none-any.whl |
|---|---|
| Size | 11.8 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
a8941eb48682d0be012a6e81b74c7e084b0446bdd5370dc10d476d7a553a7ebe
|
|
BLAKE2b-256 checksum How to use checksums |
5aae8a7b4e885acc7ceeea117890042303edfb4d59e651973d5185ff0694182a
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.9.5
|