File-backed pydantic configuration with migration support
Project description
fluxconf
File-backed Pydantic configuration with migration support.
Installation
pip install fluxconf
or with uv:
uv add fluxconf
Usage
ConfigIO
ConfigIO is a generic base class for reading and writing YAML-backed Pydantic models. Subclass it, set file_name and config_type, and you get type-safe read/write with automatic migration support.
from pydantic import BaseModel
from fluxconf import ConfigIO
class AppConfig(BaseModel):
name: str = "my-app"
debug: bool = False
class AppConfigIO(ConfigIO[AppConfig]):
file_name = "app.yml"
config_type = AppConfig
# Write
io = AppConfigIO("~/.config/my-app")
io.write(AppConfig(name="my-app", debug=True))
# Read
config = io.read()
Migrations
Define migration functions keyed by the integer version they migrate to. Migrations run automatically on read() when the stored version is behind the latest known migration.
Inherit from VersionedBaseModel instead of Pydantic's BaseModel so that the version field is preserved when the config is written back to disk via write():
from fluxconf import ConfigIO, VersionedBaseModel
class AppConfig(VersionedBaseModel):
name: str = "my-app"
debug: bool = False
def migrate_to_v2(data: dict) -> dict:
"""Rename 'use_foo' → 'foo_enabled'."""
if "use_foo" in data:
data["foo_enabled"] = data.pop("use_foo")
return data
class AppConfigIO(ConfigIO[AppConfig]):
file_name = "app.yml"
config_type = AppConfig
migrations = {
"2_rename_foo": migrate_to_v2,
}
Migration keys are strings of the form "N_description" — the integer prefix determines ordering and is stored in the config file as version.
On read(), pending migrations are applied in version order, the result is written back to disk, and the parsed model is returned.
If a migration fails, MigrationError is raised with last_successful_migration (an int). If the stored version is ahead of all known migrations, a ValueError is raised immediately.
Directory-based migrations
For larger migration sets, point migrations_dir at a directory of individual N_description.py files instead of (or in addition to) the inline migrations dict:
myapp/migrations/
1_rename_foo.py
2_add_bar.py
_helpers.py # skipped (starts with _)
Each file must define a top-level migrate(data: dict) -> dict function:
# myapp/migrations/1_rename_foo.py
def migrate(data: dict) -> dict:
if "use_foo" in data:
data["foo_enabled"] = data.pop("use_foo")
return data
from pathlib import Path
from fluxconf import ConfigIO
class AppConfigIO(ConfigIO[AppConfig]):
file_name = "app.yml"
config_type = AppConfig
migrations_dir = Path(__file__).parent / "migrations"
Only .py files with an integer prefix are loaded. Files starting with _ or without an integer prefix are silently skipped, so helper modules can live alongside migration files.
migrations and migrations_dir can be used together — fluxconf merges them, raising ValueError on key collisions.
License
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 fluxconf-0.0.1.tar.gz.
File metadata
- Download URL: fluxconf-0.0.1.tar.gz
- Upload date:
- Size: 53.6 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1d10e6d737bb50d52452019c85ecb015462d33ef3b8475053bbd5da40cc20bb1
|
|
| MD5 |
f9cf1b5c658423b7a5e0a346e2217a30
|
|
| BLAKE2b-256 |
233fe6518e37cd38c2137c4da1b7c7f137335bd8a2dd52bb93711a1c448ae63f
|
File details
Details for the file fluxconf-0.0.1-py3-none-any.whl.
File metadata
- Download URL: fluxconf-0.0.1-py3-none-any.whl
- Upload date:
- Size: 10.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
2709c861e1117ebeb6e3d09efa67f986cc5a6d3cf9b1e4440ad49cc3d72588f1
|
|
| MD5 |
79d61b15e01cd3839b4b0f230f32493c
|
|
| BLAKE2b-256 |
18931220b61f488233772eecfecc85fdbcb3ed2dce11c29fa879514ace5914e3
|