From a6db78e5d4c3e4233d78508d6b851cd1bd80638a Mon Sep 17 00:00:00 2001 From: Joffrey F Date: Fri, 10 Mar 2017 14:50:26 -0800 Subject: [PATCH] Enable variable substitution in config.secrets Signed-off-by: Joffrey F --- compose/config/config.py | 9 +++++ tests/unit/config/config_test.py | 52 +++++++++++++++++-------- tests/unit/config/interpolation_test.py | 27 ++++++++++++- 3 files changed, 70 insertions(+), 18 deletions(-) diff --git a/compose/config/config.py b/compose/config/config.py index 5d74fc76f..413f1d319 100644 --- a/compose/config/config.py +++ b/compose/config/config.py @@ -218,6 +218,8 @@ class Config(namedtuple('_Config', 'version services volumes networks secrets')) :type volumes: :class:`dict` :param networks: Dictionary mapping network names to description dictionaries :type networks: :class:`dict` + :param secrets: Dictionary mapping secret names to description dictionaries + :type secrets: :class:`dict` """ @@ -491,6 +493,13 @@ def process_config_file(config_file, environment, service_name=None): config_file.get_networks(), 'network', environment) + if config_file.version in (V3_1,): + processed_config['secrets'] = interpolate_config_section( + config_file, + config_file.get_secrets(), + 'secrets', + environment + ) elif config_file.version == V1: processed_config = services else: diff --git a/tests/unit/config/config_test.py b/tests/unit/config/config_test.py index fe896d8b5..93bae9726 100644 --- a/tests/unit/config/config_test.py +++ b/tests/unit/config/config_test.py @@ -1821,6 +1821,23 @@ class ConfigTest(unittest.TestCase): } } + def test_empty_environment_key_allowed(self): + service_dict = config.load( + build_config_details( + { + 'web': { + 'build': '.', + 'environment': { + 'POSTGRES_PASSWORD': '' + }, + }, + }, + '.', + None, + ) + ).services[0] + self.assertEqual(service_dict['environment']['POSTGRES_PASSWORD'], '') + def test_merge_pid(self): # Regression: https://github.com/docker/compose/issues/4184 base = { @@ -2335,22 +2352,23 @@ class InterpolationTest(unittest.TestCase): self.assertIn('in service "web"', cm.exception.msg) self.assertIn('"${"', cm.exception.msg) - def test_empty_environment_key_allowed(self): - service_dict = config.load( - build_config_details( - { - 'web': { - 'build': '.', - 'environment': { - 'POSTGRES_PASSWORD': '' - }, - }, - }, - '.', - None, - ) - ).services[0] - self.assertEqual(service_dict['environment']['POSTGRES_PASSWORD'], '') + @mock.patch.dict(os.environ) + def test_interpolation_secrets_section(self): + os.environ['FOO'] = 'baz.bar' + config_dict = config.load(build_config_details({ + 'version': '3.1', + 'secrets': { + 'secretdata': { + 'external': {'name': '$FOO'} + } + } + })) + assert config_dict.secrets == { + 'secretdata': { + 'external': {'name': 'baz.bar'}, + 'external_name': 'baz.bar' + } + } class VolumeConfigTest(unittest.TestCase): @@ -3663,4 +3681,4 @@ class SerializeTest(unittest.TestCase): serialized_config = yaml.load(serialize_config(config_dict)) serialized_service = serialized_config['services']['web'] assert secret_sort(serialized_service['secrets']) == secret_sort(service_dict['secrets']) - assert serialized_config['secrets'] == secrets_dict + assert 'secrets' in serialized_config diff --git a/tests/unit/config/interpolation_test.py b/tests/unit/config/interpolation_test.py index fd40153d2..256c74d9b 100644 --- a/tests/unit/config/interpolation_test.py +++ b/tests/unit/config/interpolation_test.py @@ -75,7 +75,32 @@ def test_interpolate_environment_variables_in_volumes(mock_env): }, 'other': {}, } - value = interpolate_environment_variables("2.0", volumes, 'volume', mock_env) + value = interpolate_environment_variables("2.0", volumes, 'volume', mock_env) + assert value == expected + + +def test_interpolate_environment_variables_in_secrets(mock_env): + secrets = { + 'secretservice': { + 'file': '$FOO', + 'labels': { + 'max': 2, + 'user': '${USER}' + } + }, + 'other': None, + } + expected = { + 'secretservice': { + 'file': 'bar', + 'labels': { + 'max': 2, + 'user': 'jenny' + } + }, + 'other': {}, + } + value = interpolate_environment_variables("3.1", secrets, 'volume', mock_env) assert value == expected