Update from_yaml() method

This commit is contained in:
Roman Mogylatov 2021-01-24 08:32:50 -05:00
parent 0b48f38f13
commit fbf01c0f3b
3 changed files with 4075 additions and 3916 deletions

File diff suppressed because it is too large Load Diff

View File

@ -1339,7 +1339,7 @@ cdef class ConfigurationOption(Provider):
current_config = {}
self.override(merge_dicts(current_config, config))
def from_yaml(self, filepath, loader=None):
def from_yaml(self, filepath, required=UNDEFINED, loader=None):
"""Load configuration from the yaml file.
Loaded configuration is merged recursively over existing configuration.
@ -1347,6 +1347,9 @@ cdef class ConfigurationOption(Provider):
:param filepath: Path to the configuration file.
:type filepath: str
:param required: When required is True, raise an exception if file does not exist.
:type required: bool
:param loader: YAML loader, :py:class:`YamlLoader` is used if not specified.
:type loader: ``yaml.Loader``
@ -1367,7 +1370,9 @@ cdef class ConfigurationOption(Provider):
with open(filepath) as opened_file:
config = yaml.load(opened_file, loader)
except IOError as exception:
if self._is_strict_mode_enabled() and exception.errno in (errno.ENOENT, errno.EISDIR):
if required is not False \
and (self._is_strict_mode_enabled() or required is True) \
and exception.errno in (errno.ENOENT, errno.EISDIR):
exception.strerror = 'Unable to load configuration file {0}'.format(exception.strerror)
raise
return
@ -1648,7 +1653,7 @@ cdef class Configuration(Object):
current_config = {}
self.override(merge_dicts(current_config, config))
def from_yaml(self, filepath, loader=None):
def from_yaml(self, filepath, required=UNDEFINED, loader=None):
"""Load configuration from the yaml file.
Loaded configuration is merged recursively over existing configuration.
@ -1656,6 +1661,9 @@ cdef class Configuration(Object):
:param filepath: Path to the configuration file.
:type filepath: str
:param required: When required is True, raise an exception if file does not exist.
:type required: bool
:param loader: YAML loader, :py:class:`YamlLoader` is used if not specified.
:type loader: ``yaml.Loader``
@ -1675,7 +1683,9 @@ cdef class Configuration(Object):
with open(filepath) as opened_file:
config = yaml.load(opened_file, loader)
except IOError as exception:
if self._is_strict_mode_enabled() and exception.errno in (errno.ENOENT, errno.EISDIR):
if required is not False \
and (self._is_strict_mode_enabled() or required is True) \
and exception.errno in (errno.ENOENT, errno.EISDIR):
exception.strerror = 'Unable to load configuration file {0}'.format(exception.strerror)
raise
return

View File

@ -565,6 +565,25 @@ class ConfigFromYamlTests(unittest.TestCase):
with self.assertRaises(IOError):
self.config.option.from_yaml('./does_not_exist.yml')
def test_required_file_does_not_exist(self):
with self.assertRaises(IOError):
self.config.from_yaml('./does_not_exist.yml', required=True)
def test_required_option_file_does_not_exist(self):
with self.assertRaises(IOError):
self.config.option.from_yaml('./does_not_exist.yml', required=True)
def test_not_required_file_does_not_exist_strict_mode(self):
self.config = providers.Configuration(strict=True)
self.config.from_yaml('./does_not_exist.yml', required=False)
self.assertEqual(self.config(), {})
def test_not_required_option_file_does_not_exist_strict_mode(self):
self.config = providers.Configuration(strict=True)
self.config.option.from_yaml('./does_not_exist.yml', required=False)
with self.assertRaises(errors.Error):
self.config.option()
def test_no_yaml_installed(self):
@contextlib.contextmanager
def no_yaml_module():