Skip to main content

Simple configurations management for applications.

Project description

https://travis-ci.org/LudditeLabs/config-source.svg?branch=master

This package provides extensible configuration loading from various sources.

Features:

  • Dict-like configuration loading from:

    • python dictionaries

    • python objects

    • python files

    • environment variables

    • JSON files

  • Custom configuration sources and objects.

Basically config-source provides a way to register configuration loaders and call them by names. The loader accepts optional arguments, reads configuration from a specific source and populates a configuration object.

Example:

from config_source import DictConfig
from config_source import DictConfigLoader

config = DictConfig()
config.load_from('pyfile', '/path/to/config.py')
config.load_from('json', '/path/to/config.json')
config.load_from('env', prefix='MYCFG_')

loader = DictConfigLoader(config)
loader.load('/path/to/config.py')
loader.load('/path/to/config.json')
loader.load(SomeClassWithConfigs)

Usage

Out of the box you could use:

  • Low level load_to() function.

  • DictConfig class.

  • DictConfigLoader class to assist in configurations loading.

load_to() calls a loader registered for a specific source and populates a config object passed to it:

load_to(config, 'source_name', ...)
  • config - configuration object to populate.

  • source_name - configuration source name.

DictConfig behaves like a regular python dictionary and provides load_from method to load configurations from various sources (it uses load_to() internally):

config = DictConfig()
config.load_from(<source_name>, *args, **kwargs)
  • <source_name> - configuration source name;

  • *args and **kwargs - arguments for configuration loader.

The following sources are provided out of the box for dict-like configurations.

Note: dict-like means any object with mapping interface can be used as configuration object:

config = {}
load_to(config, 'env', ...)

dictconfig = DictConfig()
dictconfig.load_from('env', ...)
load_to(dictconfig, 'env', ...)
  • object - load configuration from a python object. It reads attributes with uppercase names:

    config.load_from('object', <object>)

    Example:

    class MyConfig:
        SECRET_KEY = 123
        DEBUG = False
    
    ...
    
    config.load_from('object', MyConfig)
  • dict - load configuration from a python dictionary. Reads only uppercase keys:

    config.load_from('dict', <dict>)

    Example:

    myconfig = dict(SECRET_KEY=123, DEBUG=False)
    config.load_from('dict', myconfig)
  • env - load configuration from current runtime environment:

    config.load_from('env', prefix=<name_prefix>, trim_prefix=True)
    • prefix - Environment variable name prefix.

    • trim_prefix - Include or not prefix to result config name

    Example:

    # Load vars with names MYCFG_*, like MYCFG_SECRET.
    config.load_from('env', prefix='MYCFG_')
  • pyfile - load configuration from a python file. Reads only uppercase attributes:

    config.load_from('env', filename, silent=False)
    • filename - filename to load.

    • silent - Don’t raise an error on missing files.

    Example:

    config.load_from('pyfile', 'config.py')
  • json - load configuration from a json file. Reads only uppercase keys:

    config.load_from('json', filename, silent=False)
    • filename - filename to load.

    • silent - Don’t raise an error on missing files.

    Example:

    config.load_from('json', '/path/to/config.json')

DictConfigLoader auto-detects source name from input configuration source:

loader = DictConfigLoader(config)
loader.load('/path/to/file.py')

# Same as:
config.load_from('pyfile', '/path/to/file.py')

You may subclass to extend auto-detection.

Add source

config_source decorator is used to register additional configuration sources:

from config_source import config_source

@config_source('source_name')
def myloader(config, arg1, arg2):
    config['XX'] = arg1 + arg2

config.load_from('source_name', 1, arg2=2)

Configuration loader must be a callable with at least one argument - configuration object to populate. Other arguments are optional and loader specific.

There is a possibility to register configuration sources by implementing a package with entry point:

setup(
    ...
    entry_points={'config_source.sources': '<source> = <package name>'},
    ...
)

In the package you use config_source decorator.

For more info on entry points see

Note: you could specify single entry point even if your package adds multiple sources.

Defaults

Instead of always passing parameters to configuration loaders you could set defaults in DictConfig:

config = DictConfig(defaults={
    'env': {'prefix': 'MYAPP_'},
    'pyfile': {'filename': '/path/to/file.py'}
})

# 'prefix' will be set to MYAPP_ for 'env' config source.
# Load from 'MYAPP_*' vars by default.
config.load_from('env')

# Load from 'MY_*' vars
config.load_from('env', 'MY_')

# Load from '/path/to/file.py' by default.
config.load_from('pyfile')

# Load from '/path/to/another/file.py'.
config.load_from('pyfile', '/path/to/another/file.py')

defaults is a map where keys are source names and values are keyword parameters to be passed to loaders.

Custom configuration type

You can register configuration source for specific type (by default it’s a dict):

@config_source('source_name', config_type='mytype')
def mytype_loader(config):
    ....

config_type here is a string defining configuration object type.

Now you populate your config object using that loader:

load_to(config, 'source_name', config_type='mytype')

where config is object implementing mytype interface.

list configuration example:

from config_source import config_source, load_to


@config_source('object', config_type='list')
def object_loader(config, obj):
has = False
for key in dir(obj):
    if key.isupper():
        has = True
        config.append(getattr(obj, key))
return has


class MyConfig:
    SECRET = 1
    DEBUG = False


cfg = []
load_to(cfg, 'object', config_type='list')

# cfg = [1, False]

# Fails because by default it calls loader for 'dict' configuration.
# load_to(cfg, 'object')

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

config-source-0.0.8.tar.gz (7.7 kB view details)

Uploaded Source

Built Distribution

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

config_source-0.0.8-py3-none-any.whl (11.3 kB view details)

Uploaded Python 3

File details

Details for the file config-source-0.0.8.tar.gz.

File metadata

  • Download URL: config-source-0.0.8.tar.gz
  • Upload date:
  • Size: 7.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/1.12.1 pkginfo/1.5.0.1 requests/2.21.0 setuptools/40.7.3 requests-toolbelt/0.9.1 tqdm/4.30.0 CPython/3.5.2

File hashes

Hashes for config-source-0.0.8.tar.gz
Algorithm Hash digest
SHA256 15cfc26c0bac969be2f3f51c0dcbff0ec934e94292ecc0aa2651f0acd5292071
MD5 e1595324eb6896077315c8b445933ecf
BLAKE2b-256 c7a03f5017b47958d2eafcf6e9d71b95c7f6c1dd39df59a12d85223cc589636e

See more details on using hashes here.

File details

Details for the file config_source-0.0.8-py3-none-any.whl.

File metadata

  • Download URL: config_source-0.0.8-py3-none-any.whl
  • Upload date:
  • Size: 11.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/1.12.1 pkginfo/1.5.0.1 requests/2.21.0 setuptools/40.7.3 requests-toolbelt/0.9.1 tqdm/4.30.0 CPython/3.5.2

File hashes

Hashes for config_source-0.0.8-py3-none-any.whl
Algorithm Hash digest
SHA256 155c87fb730db914787bd57520a0bdc40a759fbbe16ab4cc43904bfa59dc65d5
MD5 4b5cb1b8af513a928a25d6556c3de7c8
BLAKE2b-256 0d42c4478aa0440db4e646d17343fdd1e37977a11e8e291916417258160a59a3

See more details on using hashes here.

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