feat(python-naive): Add concept of non-overridable globals
This commit is contained in:
		| @@ -26,17 +26,20 @@ class CONST(object): | ||||
|     CFG_THIS_FILE_DIRNAME = os.path.dirname(__file__) | ||||
|     CFG_DEFAULT_FILENAME = "config.ini" | ||||
|     CFG_DEFAULT_ABS_PATH = os.path.join(CFG_THIS_FILE_DIRNAME, CFG_DEFAULT_FILENAME) | ||||
|     # Values you don't have to set, these are their internal defaults | ||||
|     # Values you don't have to set, these are their internal defaults. You may optionally add a key 'is_global' equal | ||||
|     # to either True or False. By default if left off it'll be assumed False. Script will treat values where | ||||
|     # 'is_global' equals True as not being overridable in a '[section]'. It's a setting that only makes sense in a | ||||
|     # global context for the entire script. | ||||
|     CFG_KNOWN_DEFAULTS = [ | ||||
|         {"key": "self_name", "value": "{{ cookiecutter.__project_slug }}"}, | ||||
|         {"key": "tmp_base_dir", "value": os.path.join(CFG_THIS_FILE_DIRNAME, "data/tmp/%(self_name)s")}, | ||||
|         {"key": "state_base_dir", "value": os.path.join(CFG_THIS_FILE_DIRNAME, "data/var/lib/%(self_name)s")}, | ||||
|         {"key": "state_files_dir", "value": "%(state_base_dir)s/state"}, | ||||
|         {"key": "state_file_retention", "value": "50"}, | ||||
|         {"key": "state_file_name_prefix", "value": "state-"}, | ||||
|         {"key": "state_file_name_suffix", "value": ".log"}, | ||||
|         {"key": "{{ cookiecutter.__project_slug_under }}_some_option", "value": "http://localhost:8000/api/query"}, | ||||
|         {"key": "another_option", "value": "first"} | ||||
|         {"key": "state_files_dir", "value": "%(state_base_dir)s/state", "is_global": False}, | ||||
|         {"key": "state_file_retention", "value": "50", "is_global": False}, | ||||
|         {"key": "state_file_name_prefix", "value": "state-", "is_global": False}, | ||||
|         {"key": "state_file_name_suffix", "value": ".log", "is_global": False}, | ||||
|         {"key": "{{ cookiecutter.__project_slug_under }}_some_option", "value": "http://localhost:8000/api/query", "is_global": True}, | ||||
|         {"key": "another_option", "value": "first", "is_global": True} | ||||
|     ] | ||||
|     # In all sections other than 'default' the following settings are known and accepted. We silently ignore other | ||||
|     # settings. We use 'is_mandatory' to determine if we have to raise errors on missing settings. | ||||
| @@ -89,6 +92,7 @@ class ConfigParser( | ||||
|  | ||||
| ini_defaults = [] | ||||
| internal_defaults = {default["key"]: default["value"] for default in CONST.CFG_KNOWN_DEFAULTS} | ||||
| internal_globals = [default["key"] for default in CONST.CFG_KNOWN_DEFAULTS if default["is_global"]] | ||||
| config = ConfigParser(defaults=internal_defaults) | ||||
| config.read(CONST.CFG_DEFAULT_ABS_PATH) | ||||
|  | ||||
| @@ -106,14 +110,19 @@ def validate_default_section( | ||||
|         sys.exit(1) | ||||
|     if config.defaults(): | ||||
|         {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(f"Symbol legend:\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"* Global default from section '[{config_obj.default_section}]'\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"* Default from section '[{config_obj.default_section}]'\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f": Global option from '[{config_obj.default_section}]', can not be overridden in local sections\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"~ Local option, doesn't exist in '[{config_obj.default_section}]'\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"+ Local override of a value from '[{config_obj.default_section}]'\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"= Local override, same value as in '[{config_obj.default_section}]'") | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"= Local override, same value as in '[{config_obj.default_section}]'\n" | ||||
|               {% if cookiecutter.rich_logging == "yes" %}    {% endif %}f"# Local attempt at overriding a global, will be ignored") | ||||
|         {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(print_section_header(config_obj.default_section)) | ||||
|         for default in config_obj.defaults(): | ||||
|             ini_defaults.append({default: config_obj[config_obj.default_section][default]}) | ||||
|             {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(f"* {default} = {config_obj[config_obj.default_section][default]}") | ||||
|             if default in internal_globals: | ||||
|                 {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(f": {default} = {config_obj[config_obj.default_section][default]}") | ||||
|             else: | ||||
|                 {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(f"* {default} = {config_obj[config_obj.default_section][default]}") | ||||
|     else: | ||||
|         {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(f"No defaults defined") | ||||
|  | ||||
| @@ -133,6 +142,11 @@ def is_default( | ||||
|     return any(config_key in ini_default for ini_default in ini_defaults) | ||||
|  | ||||
|  | ||||
| def is_global( | ||||
|         config_key: str) -> bool: | ||||
|     return config_key in internal_globals | ||||
|  | ||||
|  | ||||
| def is_same_as_default( | ||||
|         config_kv_pair: dict) -> bool: | ||||
|     return config_kv_pair in ini_defaults | ||||
| @@ -149,11 +163,17 @@ def validate_config_sections( | ||||
|         else: | ||||
|             for key in config_obj.options(this_section, no_defaults=True): | ||||
|                 kv_prefix = "~" | ||||
|                 if is_default(key): | ||||
|                 remove_from_section = False | ||||
|                 if is_global(key): | ||||
|                     kv_prefix = "#" | ||||
|                     remove_from_section = True | ||||
|                 elif is_default(key): | ||||
|                     kv_prefix = "+" | ||||
|                     if is_same_as_default({key: config_obj[this_section][key]}): | ||||
|                         kv_prefix = "=" | ||||
|                 {% if cookiecutter.rich_logging == "yes" -%}log.debug{%- else -%}print{%- endif %}(f"{kv_prefix} {key} = {config_obj[this_section][key]}") | ||||
|                 if remove_from_section: | ||||
|                     config_obj.remove_option(this_section, key) | ||||
| {%- endif %} | ||||
|  | ||||
|  | ||||
|   | ||||
		Reference in New Issue
	
	Block a user