https://github.com/maacck/bedrock-py
Modular Python framework for building applications with manifest-driven modules, dependency resolution, and lifecycle hooks.
https://github.com/maacck/bedrock-py
agentic-coding modular-design modular-framework module-system python
Last synced: 10 days ago
JSON representation
Modular Python framework for building applications with manifest-driven modules, dependency resolution, and lifecycle hooks.
- Host: GitHub
- URL: https://github.com/maacck/bedrock-py
- Owner: maacck
- License: mit
- Created: 2026-05-08T05:51:39.000Z (26 days ago)
- Default Branch: main
- Last Pushed: 2026-05-18T04:48:28.000Z (16 days ago)
- Last Synced: 2026-05-21T09:20:42.176Z (13 days ago)
- Topics: agentic-coding, modular-design, modular-framework, module-system, python
- Language: Python
- Homepage: https://bedrock-py.com
- Size: 1.28 MB
- Stars: 0
- Watchers: 0
- Forks: 0
- Open Issues: 7
-
Metadata Files:
- Readme: README.md
- Changelog: CHANGELOG.md
- Contributing: CONTRIBUTING.md
- License: LICENSE
- Codeowners: .github/CODEOWNERS
- Security: SECURITY.md
- Agents: AGENTS.md
Awesome Lists containing this project
README
# Bedrock
A modular Python application framework with manifest-driven module loading, lifecycle management, and contrib modules for common capabilities.
Framework-agnostic core — no HTTP dependency in the runtime.
## Status
**Early-stage (0.1.0).** The core runtime works and is under active development, but APIs may change.
What exists today:
- Module registry with dependency resolution and lifecycle hooks
- Dependency injection container with singleton/transient/scoped lifetimes
- Hook system for structured call/response extension points (sync, async, robust)
- SQLAlchemy 2.0 database layer with Alembic migrations
- Cache system with memory and Redis.
- Signal/event system (inspired by Blinker)
- Typer-based CLI for module and database management
- Utility library (lazy loading, introspection)
What's still planned:
- Additional contrib modules
- Broader test coverage (currently: signal, cache schema, cache locks, lazy settings)
## Quick start
```bash
# Install from PyPI
uv add bedrock-core
# Or install from source for local development
git clone https://github.com/maacck/bedrock-py.git
cd bedrock-py
uv sync --all-packages
# Verify
uv run bedrock -v
# Run tests
uv run pytest packages/bedrock/tests/
```
### Basic usage
```python
import bedrock
# Initialize the runtime (discovers and loads modules)
bedrock.setup()
# Access key singletons
from bedrock.module import apps # ModuleRegistry
from bedrock.database import db # DatabaseManager
```
## Monorepo structure
This repository is a `uv` workspace:
```
packages/
├── bedrock/ # Core runtime
└──bedrock-cli/ # Scaffolding CLI (early, 0.0.1)
```
## Core runtime (`packages/bedrock`)
### Standard module structure
```
my_app/
├── __init__.py
├── manifest.yaml # Module identity and dependencies
├── models.py # SQLAlchemy models (optional)
├── entities.py # Pydantic models for validation
├── service.py # Business logic
├── exc.py # Module exceptions
└── bootstrap.py # Lifecycle hooks
```
### Module system
Manifest-driven module loading with explicit dependency management:
```python
from bedrock.module.registry import ModuleRegistry
apps = ModuleRegistry()
apps.install("inventory") # Validates dependencies, loads in order
apps.populate() # Runs on_load hooks for all modules
```
**Module manifest** (`manifest.yaml`):
```yaml
title: inventory
description: Inventory management module
version: 0.1.0
depends_on:
- products
- warehouse
commands: "commands:app" # Optional: Typer app for CLI integration
```
**Lifecycle hooks** (in `bootstrap.py`):
Bedrock always calls bootstrap hooks with keyword arguments. Hooks should explicitly declare the named parameters they need using keyword-only signatures:
```python
def on_load(*, registry, app):
"""Called when module is first loaded.
registry=ModuleRegistry, app=AppConfig
"""
pass
def ready(*, registry, app):
"""Called when all modules are loaded and ready."""
pass
def on_shutdown(*, registry, app):
"""Called during graceful shutdown."""
pass
```
Available named parameters (`registry`, `app`, `container`, `hooks`) are injected by the registry based on what each hook declares:
```python
def on_load(*, registry, app, container, hooks):
"""All four parameters available: registry, app, container, hooks"""
pass
```
### Dependency injection
Lightweight DI container with three service lifetimes:
```python
from bedrock.di import container, provider, inject, Lifetime
@provider
class MyService:
pass
@inject(svc=MyService)
def do_work(*, svc):
svc.do_something()
# Override for tests
with container.override(MyService, FakeService()):
do_work()
```
### Hook system
Structured extension points where modules declare specs and register implementations:
```python
from bedrock.hooks import hooks
ns = hooks.namespace("auth")
@ns.spec
def authenticate(user, password): ...
@ns.impl(priority=10)
def check_password(user, password): ...
ns.call("authenticate", user="alice", password="s3cret")
```
### Database layer
SQLAlchemy 2.0 integration with declarative models, session management, and Alembic migrations:
```python
from bedrock.database import db, BedrockModel
from sqlalchemy import Column, String, Integer
class Product(BedrockModel):
__tablename__ = "products"
id = Column(Integer, primary_key=True)
name = Column(String(100), nullable=False)
# Transactional session management
with db.session_scope() as session:
product = Product(name="Widget")
session.add(product)
# Query builder with filters, sorting, pagination
from bedrock.database.service import search_filter_sort_paginate
with db.session_scope() as session:
results = search_filter_sort_paginate(
db_session=session,
model=Product,
filter_specs=[{"field": "name", "op": "ilike", "value": "%widget%"}],
sort_key="name",
page=1,
limit=20,
)
```
**CLI for migrations:**
```bash
bedrock db revision --message "add products table"
bedrock db upgrade
bedrock db history
```
## CLI commands
```bash
# Module management
bedrock app inspect # Validate manifest and bootstrap
bedrock app info # Display module details
bedrock app install # Run migrations and hooks
# Database migrations
bedrock db revision --message "description"
bedrock db upgrade [revision]
bedrock db downgrade [revision]
bedrock db heads # Show latest revisions
bedrock db current # Show current revision
bedrock db history # Show migration history
# Run module commands
bedrock run # Execute module-specific CLI
```
## Dependencies
**Core runtime:**
- `pydantic` / `pydantic-settings` — Data validation and settings
- `sqlalchemy` >= 2.0 — Database ORM
- `alembic` — Database migrations
- `pyyaml` — Manifest parsing
- `loguru` — Logging
- `orjson` — Fast JSON serialization
- `typer` — CLI framework
**Optional:**
- `redis` — Redis cache backend (`uv add bedrock-core[cache-redis]`)
## Architecture principles
1. **Framework-agnostic core** — No HTTP dependencies in the module system
2. **Explicit modularity** — Manifests declare identity and dependencies
3. **Clean layer boundaries** — Models → Entities → Services → API
4. **Predictable conventions** — Strict structure for humans and AI
## Testing
```bash
uv run pytest packages/bedrock/tests/
```
Coverage is limited — currently covers signal system and lazy settings.
## Documentation
Docs site source lives in `docs-web/` (Fumadocs/Next.js):
```bash
cd docs-web
pnpm install
pnpm dev
```
## License
Bedrock is licensed under the MIT License. See [LICENSE](LICENSE) for details.