pycolib/configparser.py
author Radek Brich <radek.brich@devl.cz>
Wed, 09 Jul 2014 17:56:48 +0200
changeset 15 497067ee16b7
parent 12 d5f749032fa1
permissions -rw-r--r--
Update setup.py: Do not rename the package to python3-pycolib for bdist_rpm target. This should be done by packager if needed.

import os.path


class ConfigParserError(Exception):
    pass


class ConfigParser:

    """
    Simple config file parser utilizing Python's exec() builtin.
    """

    def __init__(self):
        self.options = {}
        self.values = {}

    def add_option(self, name, type=str, default=None):
        """Register option name, type and default value."""
        self.options[name] = {'type':type, 'default':default}
        self.values[name] = default

    def load(self, fname, must_exist=True):
        """Read config file and check loaded values."""
        if not must_exist and not os.path.isfile(fname):
            return
        self.read(fname)
        self.check()

    def read(self, fname):
        """Read config file. Does not check values."""
        with open(fname) as f:
            exec(f.read(), self.values)

    def check(self):
        """Check option values against registered types."""
        for key in self.values.keys():
            if key == '__builtins__':
                continue
            if key in self.options:
                type_ = self.options[key]['type']
                if not isinstance(self.values[key], type_) and not self.values[key] is None:
                    raise ConfigParserError("Bad value of config parameter '%s': type is %s but should be %s"
                        % (key, type(self.values[key]), type_))
            else:
                raise ConfigParserError("Unknown config parameter '%s'." % key)

    def __getattr__(self, name):
        """Attribute access for config parameters.

        cfg.my_param <===> cfg.values['myparam']

        """
        if name in self.values:
            return self.values[name]
        else:
            raise AttributeError()