用于将配置从文件和环境变量加载到类的python模块
cklass的Python项目详细描述
类
从文件和环境变量到类的分层配置加载器。
此模块负责加载配置文件、机密文件 和环境变量到单个配置类没有麻烦!
特点:
- 易于使用(只有一个功能!)并配置
- 带有正常的默认值
- 重要性的逻辑层次顺序
- 通过自定义格式加载程序支持无限数量的文件格式
- 自动查找指定目录中的配置文件和机密文件
限制条件:
- 所有键都不区分大小写
安装
pip install cklass
使用量
你所要做的就是创建一个类并调用函数
cklass.load_config()
用它作为参数。
区分大小写
类名(以及表示字典的嵌套类)
必须是大写或标题大写,例如Config
或CONFIG
会起作用,但config
不会。
要搜索和匹配的所有变量都必须大写。 这也意味着所有键都不区分大小写。
例如:
# config.yamllogin:'thiswillbeignored'password:'thiswillbeignored'uSER:logIN:'pi'paSSwoRD:'raspberry'
# secret.yamlUser:# this will overwrite `logIN` and `pasSSwoRD` from abovelogin:'root'password:'yrrebpsar'
# env variable EXPORT USER__PASSWORD='mytopsecretpassword'
# pythonimportcklassclassUser:LOGIN='this string will be overwritten'password='this will NOT be overwritten'Password='this will NOT be overwritten'PASSWORD='default password, will be overwritten'other_variable_kinda_like_private=42cklass.load_config(User)
层次结构
每个类级键都必须嵌套在名为 和班上一样。只有类属性将被覆盖, 只有通过定义 它们在配置文件中。
由cklass.load_config()
加载的每个类都有其属性
根据下面指定的顺序覆盖:
- 类代码中定义的所有值都视为默认值
- 函数将查找在
_config_filename
并在目录的_config_filepath
列表中找到 将考虑并覆盖(1)中设置的值。 - 函数将查找在
_secret_filename
并在目录的_secret_filepath
列表中找到 将考虑并覆盖(1)和(2)中设置的值。 - 函数将查找类型为
str
的匹配环境变量。 使用_environ_prefix
中定义的可选前缀并覆盖值 在(1),(2)和(3)中设置。
# pythonimportcklass# any name will workclassConfig:PATH_TO_SOMETHING='/etc/default/path/'classUser:NAME=''EMAIL=''PASS=''DEBUG=FalseclassSERVER:OPEN_PORTS=['80']SECRET_KEY=''_type_safe=True_environ_prefix='MYAPP'_config_filename='config.yaml'_secret_filename='secret.json'_config_filepath=['/etc/myapp/conf/']_secret_filepath=['.']_format_loaders={'json':['jsonlib','read'],'yaml':['metayaml','read'],}cklass.load_config(Config)
# config.yamlconfig:path-to-something:/etc/app/debug:Trueserver:open-ports:-'22'-'80'-'443'
# secret.yamlconfig:user:name:Your Secret Nameemail:example@example.com
# envvars.shexportMYAPP__CONFIG__SECRET_KEY="supersecretkey"exportMYAPP__CONFIG__USER__PASS="secretpassword"
默认值
传递给cklass.load_config()
的每个类都可以使用适当的
输入一些操作它的行为。
以下指定的所有值都视为默认值。这些变量中的任何一个都可以省略。
类型安全性
_type_safe=True
这将比较并确保config/secret文件中覆盖的所有密钥具有相同的
键入类中定义的变量,除了None
。如果设置为False
则此检查
将被跳过。
示例:Config.VALIDATE_ME = True
将只匹配配置文件中的bool
类型。Config.DOESNT_MATTER = None
将匹配配置文件和环境变量中的任何类型
CONFIG__DOESNT_MATTER
。
环境前缀
_environ_prefix=''
这允许您定义自定义环境变量前缀作为命名空间。
例如,您可以将其设置为'MYAPP'
,这将导致只查找
以这样的前缀开头的环境变量,如MYAPP__CONFIG__HOME_DIR
。
类和嵌套是用两个下划线__
定义的,因此键名可能包含
只有一个下划线-例如CORRECT_NAME
,INCORRECT___NAME
。
环境变量支持三种类型:从字符串TRUE
/FALSE
转换的bool,
如果前两次转换失败,则从包含数字和字符串的字符串转换的数字。
配置/机密文件名
_config_filename='config.yaml'_secret_filename='secret.yaml'
配置的文件名。扩展名必须与_format_loaders
中定义的扩展名匹配。
配置/机密文件路径
_config_filepath=['.']_secret_filepath=['.']
函数将在其中查找_config__filename
和_secret_filename
的路径列表。
例如,您可以将其更改为['~', '.']
,这将导致函数
在$HOME/config.yaml
中搜索config.yaml
,然后在$PWD/config.yaml
中搜索。
只考虑将成功打开的第一个文件。
格式加载程序
_format_loaders={'ini':['ini','load'],'json':['json','load'],'toml':['toml','load'],'yaml':['yaml','safe_load'],}
格式加载程序由一个具有密钥匹配文件扩展名的嵌套字典组成
和定义为两个元素列表的值。默认格式加载器启用
在ini
、json
、toml
和yaml
文件类型中。
为了使其工作,您需要安装适当的python包
在列表中指定。
示例:yaml: ['metayaml', 'read']
表示对于任何配置/机密文件
with yaml
扩展将通过metayaml
模块中定义的read
函数加载。
真实的现场示例
请参阅examples目录。
# config.pyimportcklassclassRoot:_environ_prefix='SIMPLEWEBAPP'_config_filepath=['./conf']_secret_filepath=['./conf']classCommon(Root):NAME='Simple Web App'DEBUG=TrueDATE=''BASE_DIR='/app'SRC_DIR='./src'ALLOWED_HOSTS=[]classSecret:KEY=''_config_filename='common.yaml'_secret_filename='common.json'classDatabase(Root):ENGINE='sqlite3'HOST='localhost'NAME='simplewebapp_db'PORT=1111classCredentials:USER='readonly'PASS='readonly'_config_filename='database.yaml'_secret_filename='database.json'cklass.load_config(Common)cklass.load_config(Database)print(f'''Common: NAME = '{Common.NAME}' DEBUG = {Common.DEBUG} DATE = '{Common.DATE}' BASE_DIR = '{Common.BASE_DIR}' SRC_DIR = '.{Common.SRC_DIR}' ALLOWED_HOSTS = {Common.ALLOWED_HOSTS} Secret: KEY = '{Common.Secret.KEY}'Database: ENGINE = '{Database.ENGINE}' HOST = '{Database.HOST}' NAME = '{Database.NAME}' PORT = {Database.PORT} Credentials: USER = {Database.Credentials.USER}' PASS = '{Database.Credentials.PASS}'''')
# conf/common.yaml Common:debug:noallowed-hosts:-'localhost'-'127.0.0.1'-'mydomain.local'
#conf/common.json{"Common":{"Secret":{"key":"AAAAAAAA"}}}
# conf/database.yamlDatabase:engine:postgresqlhost:psql://localhost
#conf/database.json{"database":{"credentials":{"user":"dbuser","pass":"pbpass"}}}
# conf/environment.sh#!/bin/bashexportSIMPLEWEBAPP__COMMON__DEBUG=TRUE exportSIMPLEWEBAPP__COMMON__DATE="$(date)"exportSIMPLEWEBAPP__COMMON__SECRET__KEY="seckey"exportSIMPLEWEBAPP__DATABASE__PORT=6621exportSIMPLEWEBAPP__DATABASE__CREDENTIALS__PASS="supersecretdbpass"
结果
source conf/environment.sh
python3 config.py
Common:NAME='Simple Web App'# overwritten in conf/common.yaml# then overwritten by environment variableDEBUG=True# overwritten by environment variableDATE='Mon Apr 15 12:35:39 CEST 2019'BASE_DIR='/app'SRC_DIR='./src'# overwritten in conf/common.yamlALLOWED_HOSTS=['localhost','127.0.0.1','mydomain.local']classSecret:# overwritten in conf/common.json# then overwritten by environment variableKEY='seckey'Database:# overwritten in conf/database.yamlENGINE='postgresql'HOST='psql://localhost'NAME='simplewebapp_db'# overwritten by environment variablePORT=6621classCredentials:# overwritten in conf/database.jsonUSER='dbuser'# overwritten in conf/database.json# then overwritten by environment variablePASS='supersecretdbpass'