YamlSettings
------------

A Settings Configuration Module.

.. image:: https://travis-ci.org/KyleJamesWalker/yamlsettings.svg?branch=master
    :target: https://travis-ci.org/KyleJamesWalker/yamlsettings

.. image:: https://codecov.io/gh/KyleJamesWalker/yamlsettings/branch/master/graph/badge.svg
  :target: https://codecov.io/gh/KyleJamesWalker/yamlsettings

A library to help manage project settings, without having to worry about
accidentally checking non-public information, like api keys.  Along with
environment variable support.

Example setup
^^^^^^^^^^^^^
Python Code - Base Functions

.. code-block:: python

 import yamlsettings


 app_settings = yamlsettings.load('defaults.yaml')
 app_settings.update(yamlsettings.load('settings.yaml'))
 yamlsettings.update_from_env(app_settings)
 user = app_settings.myproj.databases.primary_sql.user

defaults.yml - Default Settings for Project (tracked)

.. code-block:: yaml

 ---
 # Program Defaults, do not edit this file!!!
 # All values should be overridden in the following ways:
 # 1. In the 'settings.yaml' file.
 # 2. With environment variables. Example myproj.databases.primary_sql.user can
 #    be overridden with MYPROJ_DATABASES_PRIMARY_SQL_USER.
 myproj:
   databases:
     primary_sql:
       user: my_user
       passwd: password_here
       host: db-bouncer-01.postgres.com:5432
       db: postgres
       compress: true
       engine: postgresql
     splunk:
       user: splunk_user_here
       passwd: password here
       host: splunk.com
       port: 8089
     redis:
       redis_host: 127.0.0.1
       redis_port: 6379
   flask_config:
     DEBUG: False
     SECRET_KEY: hard key to guess and keep values secret
   debug_sql: false
   debug_profiler: false
   cache_routes: true
   logging_config:
     version: 1
     disable_existing_loggers: False
     formatters:
       light:
         format: '%(asctime)s [%(levelname).1s] %(name)s: %(message)s'
         datefmt: '%Y-%m-%d %H:%M:%S'
       verbose:
         format: '%(asctime)s %(levelname) 8s(%(name)s): %(message)s'
         datefmt: ''
     handlers:
       console:
         class: logging.StreamHandler
         level: DEBUG
         formatter: light
         stream: ext://sys.stdout
       slack:
         class: api.slackLogHandler.BufferingSlackWebHookHandler
         level: INFO
         formatter: light
         capacity: 100
         organization: KyleJamesWalker
         token: need_this
         channel: '#services'
         username: my-proj-logger
         icon_emoji: ':happy_panda:'
       noid:
         class: logging.NullHandler
     loggers:
       requests:
         level: NOTSET
         handlers: [noid]
         propagate: no
     root:
       level: NOTSET
       handlers:
         - console

settings.yml - Custom Settings (untracked)

.. code-block:: yaml

 ---
 myproj:
   databases:
     primary_sql:
       user: root
       passwd: god
     splunk:
       user: real_user
       passwd: pa$$word
   flask_config:
     SECRET_KEY: sdfasjksdfASFAS23423f@#$%!$#VR@%UQ%
   logging_config:
     handlers:
       slack:
         token: 123243294832104981209
     root:
       handlers:
         - console
         - slack

Example package resource loading

.. code-block:: python

 """Parameters that can be passed are:
  resource: The resource to load from the package (default: settings.yaml)
  env: When set the yamldict will update with env variables (default: true)
  prefix: Prefix for environment loading (default: None)
  persist: When set the yamldict will only be loaded once. (default: true)
 """
 yamlsettings.load('package://example')
 yamlsettings.load('package://example?resource=diff.yaml')
 yamlsettings.load('package://example?prefix=MY_FUN&persist=false')


Plugins
^^^^^^^

This project also supports plugins. The base project has two plugins:

- file: Loads from the file system.
- package: Loads settings from a package resource.

Example Plugin:
===============

setup.py

.. code-block:: python

 from setuptools import setup

 setup(
     name='yamlsettings-example',
     version='1.0.0',
     author='Kyle Walker',
     author_email='KyleJamesWalker@gmail.com',
     description='Quick Example',
     py_modules=['yamlsettings_example'],
     entry_points={
         'yamlsettings10': [
             'ext = yamlsettings_example:ZxcExtension',
         ],
     },
 )

yamlsettings_example.py

.. code-block:: python

 import yamlsettings


 class ZxcExtension(yamlsettings.YamlSettingsExtension):
     """Quick Example Plugin

     Standard file opener, but will merge in values passed to kwargs
     """
     protocols = ['zxc']

     @classmethod
     def load_target(cls, scheme, path, fragment, username,
                     password, hostname, port, query,
                     load_method, **kwargs):
         full_path = (hostname or '') + path
         obj = load_method(open(full_path, **query))
         obj.update(kwargs)
         return obj

usage

.. code-block:: python

 import yamlsettings
 yamlsettings.load("zxc://defaults.yaml", foo='bar')

 # Note: this is automatically detected when the extension is installed
 # alternatively the extension can be manually registered with:
 yamlsettings.registry.add(ZxcExtension)
