From 44a91e6ba8bf64ef7206f48239638bb9f042145f Mon Sep 17 00:00:00 2001 From: Ryan Brainard Date: Fri, 11 Jul 2014 10:18:05 -0700 Subject: [PATCH 1/2] Resolve environment without values to values on host For parity with the Docker CLI, allow environment variables without values to be automatically resolved to their values on the host. Signed-off-by: Ryan Brainard Conflicts: tests/integration/service_test.py --- fig/service.py | 18 ++++++++++++++++++ tests/integration/service_test.py | 21 +++++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/fig/service.py b/fig/service.py index 0c198269d0a..e3cbb2969d6 100644 --- a/fig/service.py +++ b/fig/service.py @@ -330,6 +330,11 @@ def _get_container_create_options(self, override_options, one_off=False): if 'volumes' in container_options: container_options['volumes'] = dict((split_volume(v)[1], {}) for v in container_options['volumes']) + if 'environment' in container_options: + if isinstance(container_options['environment'], list): + container_options['environment'] = dict(split_env(e) for e in container_options['environment']) + container_options['environment'] = dict(resolve_env(k,v) for k,v in container_options['environment'].iteritems()) + if self.can_be_built(): if len(self.client.images(name=self._build_tag_name())) == 0: self.build() @@ -447,3 +452,16 @@ def split_port(port): external_port = (external_ip,) return internal_port, external_port +def split_env(env): + if '=' in env: + return env.split('=', 1) + else: + return env, None + +def resolve_env(key,val): + if val is not None: + return key, val + elif key in os.environ: + return key, os.environ[key] + else: + return key, '' diff --git a/tests/integration/service_test.py b/tests/integration/service_test.py index 315e14ce31c..4700f410105 100644 --- a/tests/integration/service_test.py +++ b/tests/integration/service_test.py @@ -5,6 +5,7 @@ from fig.container import Container from fig.packages.docker.errors import APIError from .testcases import DockerClientTestCase +import os class ServiceTest(DockerClientTestCase): def test_containers(self): @@ -306,3 +307,23 @@ def test_working_dir_param(self): service = self.create_service('container', working_dir='/working/dir/sample') container = service.create_container().inspect() self.assertEqual(container['Config']['WorkingDir'], '/working/dir/sample') + + def test_split_env(self): + service = self.create_service('web', environment=['NORMAL=F1', 'CONTAINS_EQUALS=F=2', 'TRAILING_EQUALS=']) + env = service.start_container().environment + for k,v in {'NORMAL': 'F1', 'CONTAINS_EQUALS': 'F=2', 'TRAILING_EQUALS': ''}.iteritems(): + self.assertEqual(env[k], v) + + def test_resolve_env(self): + service = self.create_service('web', environment={'FILE_DEF': 'F1', 'FILE_DEF_EMPTY': '', 'ENV_DEF': None, 'NO_DEF': None}) + os.environ['FILE_DEF'] = 'E1' + os.environ['FILE_DEF_EMPTY'] = 'E2' + os.environ['ENV_DEF'] = 'E3' + try: + env = service.start_container().environment + for k,v in {'FILE_DEF': 'F1', 'FILE_DEF_EMPTY': '', 'ENV_DEF': 'E3', 'NO_DEF': ''}.iteritems(): + self.assertEqual(env[k], v) + finally: + del os.environ['FILE_DEF'] + del os.environ['FILE_DEF_EMPTY'] + del os.environ['ENV_DEF'] From d1052ff666e5bf413b88e10ec5e640daf3e7876b Mon Sep 17 00:00:00 2001 From: Ryan Brainard Date: Fri, 11 Jul 2014 10:07:50 -0700 Subject: [PATCH 2/2] Add documention for key-only environment Signed-off-by: Ryan Brainard --- docs/yml.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/docs/yml.md b/docs/yml.md index 5a5a2af6316..6204122fbc9 100644 --- a/docs/yml.md +++ b/docs/yml.md @@ -55,8 +55,11 @@ volumes: - cache/:/tmp/cache -- Add environment variables. +-- Environment variables with only a key are resolved to values on the host +-- machine, which can be helpful for secret or host-specific values. environment: RACK_ENV: development + SESSION_SECRET: ``` -- Networking mode. Use the same values as the docker client --net parameter