diff --git a/changelogs/fragments/49843-docker_container-wrap-env.yaml b/changelogs/fragments/49843-docker_container-wrap-env.yaml new file mode 100644 index 00000000000..42088b67b03 --- /dev/null +++ b/changelogs/fragments/49843-docker_container-wrap-env.yaml @@ -0,0 +1,3 @@ +--- +bugfixes: + - 'docker_container - fail when non-string env values are found, avoiding YAML parsing issues. (https://github.com/ansible/ansible/issues/49802)' diff --git a/lib/ansible/modules/cloud/docker/docker_container.py b/lib/ansible/modules/cloud/docker/docker_container.py index 81687dbb3b1..91996618be8 100644 --- a/lib/ansible/modules/cloud/docker/docker_container.py +++ b/lib/ansible/modules/cloud/docker/docker_container.py @@ -186,6 +186,8 @@ options: env: description: - Dictionary of key,value pairs. + - Values which might be parsed as numbers, booleans or other types by the YAML parser must be quoted (e.g. C("true")) in order to avoid data loss. + type: dict env_file: version_added: "2.2" description: @@ -644,7 +646,9 @@ EXAMPLES = ''' - "8080:9000" - "127.0.0.1:8081:9001/udp" env: - SECRET_KEY: ssssh + SECRET_KEY: "ssssh" + # Values which might be parsed as numbers, booleans or other types by the YAML parser need to be quoted + BOOLEAN_KEY: "yes" - name: Container present docker_container: @@ -762,8 +766,8 @@ EXAMPLES = ''' name: test image: ubuntu:18.04 env: - - arg1: true - - arg2: whatever + - arg1: "true" + - arg2: "whatever" volumes: - /tmp:/tmp comparisons: @@ -776,8 +780,8 @@ EXAMPLES = ''' name: test image: ubuntu:18.04 env: - - arg1: true - - arg2: whatever + - arg1: "true" + - arg2: "whatever" comparisons: '*': ignore # by default, ignore *all* options (including image) env: strict # except for environment variables; there, we want to be strict @@ -1605,6 +1609,9 @@ class TaskParameters(DockerBaseClass): final_env[name] = str(value) if self.env: for name, value in self.env.items(): + if not isinstance(value, string_types): + self.fail("Non-string value found for env option. " + "Ambiguous env options must be wrapped in quotes to avoid YAML parsing. Key: %s" % (name, )) final_env[name] = str(value) return final_env diff --git a/test/integration/targets/docker_container/tasks/tests/options.yml b/test/integration/targets/docker_container/tasks/tests/options.yml index a63486be94e..2c78e95bc9c 100644 --- a/test/integration/targets/docker_container/tasks/tests/options.yml +++ b/test/integration/targets/docker_container/tasks/tests/options.yml @@ -1179,6 +1179,9 @@ env: TEST1: val1 TEST2: val2 + TEST3: "False" + TEST4: "true" + TEST5: "yes" register: env_1 - name: env (idempotency) @@ -1190,6 +1193,9 @@ env: TEST2: val2 TEST1: val1 + TEST5: "yes" + TEST3: "False" + TEST4: "true" register: env_2 - name: env (less environment variables) @@ -1214,6 +1220,18 @@ force_kill: yes register: env_4 +- name: env (fail unwrapped values) + docker_container: + image: alpine:3.8 + command: '/bin/sh -c "sleep 10m"' + name: "{{ cname }}" + state: started + env: + TEST1: true + force_kill: yes + register: env_5 + ignore_errors: yes + - name: cleanup docker_container: name: "{{ cname }}" @@ -1227,6 +1245,8 @@ - env_2 is not changed - env_3 is not changed - env_4 is changed + - env_5 is failed + - "('Non-string value found for env option.') in env_5.msg" #################################################################### ## env_file #########################################################