Skip to main content

Loads configurations from different files with ease

Project description

c3a3-config-loader

Coverage Python

Seamless, pluggable configuration for Python apps — merge CLI/ENV/RC, validate, encrypt secrets, and build hierarchical CLI commands.


Why?

Reading configuration shouldn't require boilerplate. c3a3-config-loader lets you declare a YAML/JSON spec and automatically:

  • Parse command-line arguments with namespace support (--db.host)
  • Build hierarchical commands with subcommands (deploy staging --region us-east-1)
  • Pull values from environment variables (MYAPP_DB_HOST)
  • Fall back to a per-user RC file (~/.myapprc) in TOML format
  • Respect a deterministic precedence order you choose
  • Validate types, required fields, allowed values, and relationships
  • Obfuscate sensitive values using AES-256 encryption
  • Extend via plugins (vault://secret, ssm://param)

All in a 100% type-annotated, 80%+ test-covered library.


Installation

pip install c3a3-config-loader

Requires Python 3.11+. Binary wheels ship with cryptography.


Quick Start

v1.x Style: Parameters Only

from config_loader import Configuration

spec = {
    "schema_version": "1.0",
    "app_name": "myapp",
    "precedence": ["args", "env", "rc"],
    "parameters": [
        {"namespace": "db", "name": "host", "type": "string", "required": True},
        {"namespace": "db", "name": "port", "type": "number", "default": 5432},
        {"namespace": None, "name": "debug", "type": "boolean", "default": False},
    ],
}

cfg = Configuration(spec)
result = cfg.process()  # Reads sys.argv, os.environ, ~/.myapprc

print(f"Database: {result.db.host}:{result.db.port}")
print(f"Debug: {result.debug}")
python app.py --db.host localhost --debug
# Or: export MYAPP_DB_HOST=localhost

v2.0 Style: With Commands

from config_loader import Configuration

spec = {
    "schema_version": "2.0",
    "app_name": "deploy",
    "commands": [
        {
            "name": "deploy",
            "aliases": ["d"],
            "subcommands": [
                {
                    "name": "staging",
                    "terminal": True,
                    "arguments": [
                        {"name": "region", "short": "r", "type": "string", "required": True}
                    ]
                },
                {
                    "name": "production",
                    "terminal": True,
                    "arguments": [
                        {"name": "region", "type": "string", "required": True},
                        {"name": "force", "short": "f", "type": "boolean"}
                    ]
                }
            ]
        }
    ]
}

cfg = Configuration(spec)
result = cfg.process(["deploy", "staging", "--region", "us-east-1"])

print(result.command.path)       # ["deploy", "staging"]
print(result.command.arguments)  # {"region": "us-east-1"}
deploy staging --region us-east-1
deploy production -r eu-west-1 --force
d staging -r us-east-1  # Using alias

Features

Multi-Source Configuration

precedence:
  - args    # CLI arguments (highest priority)
  - env     # Environment variables
  - rc      # RC file (~/.apprc)

Validation

parameters:
  - name: port
    type: number
    min: 1
    max: 65535

  - name: environment
    type: string
    accepts: [dev, staging, prod]

Hierarchical Commands (v2.0)

commands:
  - name: deploy
    subcommands:
      - name: staging
        terminal: true
      - name: production
        terminal: true

Argument Inheritance (v2.0)

commands:
  - name: deploy
    arguments:
      - name: verbose
        scope: inherited  # Available in all subcommands

Exclusion Groups (v2.0)

exclusion_groups:
  - name: output-format
    arguments: [json, yaml, table]
    message: "Choose one output format"

Dependency Rules (v2.0)

dependency_rules:
  - name: notify-needs-email
    rule: if_then
    if_arg: notify
    then_require: [email]

Value Providers (v2.0)

arguments:
  - name: region
    values_from: myapp.providers.get_regions
def get_regions(ctx):
    return ["us-east-1", "us-west-2", "eu-west-1"]

Builder Pattern (v2.0)

builder = cfg.builder()
builder = builder.add_command("deploy")
suggestions = builder.check_next()  # Available arguments
builder = builder.add_argument("region", "us-east-1")
result = builder.build()

Secret Obfuscation

parameters:
  - name: password
    obfuscated: true
print(result.db.password)       # obfuscated:...
print(cfg.reveal(result.db.password))  # actual value

Protocol Plugins

from config_loader import ConfigPlugin, PluginManifest

class VaultPlugin(ConfigPlugin):
    @property
    def manifest(self):
        return PluginManifest(protocol="vault", type="string", sensitive=True)

    def load_value(self, value):
        return vault_client.read(value)

cfg = Configuration(spec, plugins=[VaultPlugin()])
myapp --db.password vault://secrets/db/password

Documentation

Full documentation follows the Divio documentation system:


Version History

Version Features
2.0 Hierarchical commands, value providers, builder pattern, deprecation
1.x Parameters, CLI/ENV/RC merging, validation, encryption, plugins

v2.0 is fully backward compatible with v1.x specs.


Development

git clone https://github.com/your-org/c3a3-config-loader.git
cd c3a3-config-loader
pip install -e .[dev]

# Run tests
pytest -q

# Type checking
mypy --strict -p config_loader

# Linting
ruff check --fix src/ tests/

License

SPDX-License-Identifier: Prosperity-3.0.0

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

c3a3_config_loader-2.0.0.tar.gz (157.4 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

c3a3_config_loader-2.0.0-py3-none-any.whl (63.6 kB view details)

Uploaded Python 3

File details

Details for the file c3a3_config_loader-2.0.0.tar.gz.

File metadata

  • Download URL: c3a3_config_loader-2.0.0.tar.gz
  • Upload date:
  • Size: 157.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.7

File hashes

Hashes for c3a3_config_loader-2.0.0.tar.gz
Algorithm Hash digest
SHA256 956aa3a7624c5120c47b97aeb20ebe930ac831ee95c7919eafc34fb264530d15
MD5 baafb6c3295d9a9525093d2d2977be2b
BLAKE2b-256 daa0f62c1b1239a1b4769dbbbe558e0cec3faa52e49ff99b1cd0c4e38356e518

See more details on using hashes here.

Provenance

The following attestation bundles were made for c3a3_config_loader-2.0.0.tar.gz:

Publisher: ci.yml on mrtu/c3a3-config_loader

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file c3a3_config_loader-2.0.0-py3-none-any.whl.

File metadata

File hashes

Hashes for c3a3_config_loader-2.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 39d8b9ec060ddee616b40114e59d01af74078b8243a444fd8cb20c2d7042900c
MD5 1083c6ee8406a62ba4a459d94f28f65b
BLAKE2b-256 96ea8419179cdf235103cb42811f8d605b376ce32885e8f9fc7e13d1230beb16

See more details on using hashes here.

Provenance

The following attestation bundles were made for c3a3_config_loader-2.0.0-py3-none-any.whl:

Publisher: ci.yml on mrtu/c3a3-config_loader

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page