diff --git a/tripleo_ansible/ansible_plugins/filter/helpers.py b/tripleo_ansible/ansible_plugins/filter/helpers.py index 6eac7250b..bd0d86ba9 100644 --- a/tripleo_ansible/ansible_plugins/filter/helpers.py +++ b/tripleo_ansible/ansible_plugins/filter/helpers.py @@ -197,7 +197,8 @@ class FilterModule(object): return to_delete - def haskey(self, data, attribute, value=None, reverse=False, any=False): + def haskey(self, data, attribute, value=None, reverse=False, any=False, + excluded_keys=[]): """Return dict data with a specific key. This filter will take a list of dictionaries (data) @@ -207,10 +208,21 @@ class FilterModule(object): which have the attribute. If any is set to True, the returned list will match any value in the list of values for "value" parameter which has to be a list. + If we want to exclude items which have certain key(s); these keys + should be added to the excluded_keys list. If excluded_keys is used + with reverse, we'll just exclude the items which had a key from + excluded_keys in the reversed list. """ return_list = [] for i in data: + to_skip = False for k, v in json.loads(json.dumps(i)).items(): + for e in excluded_keys: + if e in v: + to_skip = True + break + if to_skip: + break if attribute in v and not reverse: if value is None: return_list.append(i) diff --git a/tripleo_ansible/roles/tripleo_container_manage/molecule/default/converge.yml b/tripleo_ansible/roles/tripleo_container_manage/molecule/default/converge.yml index 8b2e7e4a0..646b7fd10 100644 --- a/tripleo_ansible/roles/tripleo_container_manage/molecule/default/converge.yml +++ b/tripleo_ansible/roles/tripleo_container_manage/molecule/default/converge.yml @@ -64,6 +64,7 @@ tripleo_container_manage_debug: true tripleo_container_manage_config_patterns: '*.json' tripleo_container_manage_systemd_order: true + tripleo_container_manage_valid_exit_code: [0] tasks: - include_role: name: tripleo_container_manage diff --git a/tripleo_ansible/roles/tripleo_container_manage/molecule/default/prepare.yml b/tripleo_ansible/roles/tripleo_container_manage/molecule/default/prepare.yml index 531eed45d..6948494ee 100644 --- a/tripleo_ansible/roles/tripleo_container_manage/molecule/default/prepare.yml +++ b/tripleo_ansible/roles/tripleo_container_manage/molecule/default/prepare.yml @@ -45,7 +45,7 @@ { "image": "fedora:latest", "net": "host", - "command": "sleep 3600" + "command": "sleep 5" } dest: '/tmp/container-configs/fedora_bis.json' - name: Create a third configuration file for a fedora container @@ -54,7 +54,7 @@ { "image": "fedora:latest", "net": "host", - "command": "sleep 3600" + "command": "sleep 5" } dest: '/tmp/container-configs/fedora_three.json' - name: Create old healthcheck service for fedora container diff --git a/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/check_exit_code.yml b/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/check_exit_code.yml index becd98302..f9e8d67b2 100644 --- a/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/check_exit_code.yml +++ b/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/check_exit_code.yml @@ -16,7 +16,7 @@ - name: "Wait for containers to be exited" podman_container_info: - name: "{{ batched_container_data | haskey(attribute='action', reverse=True) | list_of_keys }}" + name: "{{ containers_with_exit_code }}" register: podman_containers_infos until: ( podman_containers_infos.containers | selectattr('State.Running', 'equalto', True) |list|length ) == 0 # Retry 30 times every 10 seconds so we wait 5 min in total diff --git a/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/create.yml b/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/create.yml index 4e0f0abb1..eac971d3b 100644 --- a/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/create.yml +++ b/tripleo_ansible/roles/tripleo_container_manage/tasks/podman/create.yml @@ -97,10 +97,11 @@ when: - not ansible_check_mode|bool -- name: "Create facts for containers which changed or failed" +- name: "Create facts for containers which changed or failed or which require rc check" set_fact: containers_changed: "{{ create_async_poll_results.results | get_changed_containers }}" containers_failed: "{{ create_async_poll_results.results | get_failed_containers }}" + containers_to_check: "{{ batched_container_data | haskey(attribute='command', excluded_keys=['action', 'restart']) | list_of_keys | default([]) }}" - name: Print the containers that failed to start fail: @@ -120,6 +121,9 @@ - name: "Block for container exit codes" when: - - tripleo_container_manage_valid_exit_code|length != 0 - not ansible_check_mode|bool + - tripleo_container_manage_valid_exit_code|length != 0 + - containers_to_check|length != 0 include_tasks: podman/check_exit_code.yml + vars: + containers_with_exit_code: "{{ containers_to_check }}" diff --git a/tripleo_ansible/tests/plugins/filter/test_helpers.py b/tripleo_ansible/tests/plugins/filter/test_helpers.py index a144f6497..507357794 100644 --- a/tripleo_ansible/tests/plugins/filter/test_helpers.py +++ b/tripleo_ansible/tests/plugins/filter/test_helpers.py @@ -200,6 +200,90 @@ class TestHelperFilters(tests_base.TestCase): attribute='restart', value='always') self.assertEqual(result, expected_list) + def test_haskey_exclude(self): + data = [ + { + 'keystone': { + 'start_order': 1, + 'image': 'quay.io/tripleo/keystone', + 'command': 'sleep 10', + 'restart': 'always' + }, + }, + { + 'nova': { + 'start_order': 1, + 'image': 'quay.io/tripleo/nova', + 'command': 'sleep 10', + 'action': 'exec' + }, + }, + { + 'mysql': { + 'start_order': 0, + 'command': 'sleep 10', + 'image': 'quay.io/tripleo/mysql' + } + }, + { + 'haproxy': { + 'start_order': 0, + 'image': 'quay.io/tripleo/haproxy' + } + } + ] + expected_list = [ + { + 'mysql': { + 'start_order': 0, + 'command': 'sleep 10', + 'image': 'quay.io/tripleo/mysql' + }, + } + ] + result = self.filters.haskey(data=data, + attribute='command', + excluded_keys=['action', 'restart']) + self.assertEqual(result, expected_list) + + def test_haskey_reverse_exclude(self): + data = [ + { + 'keystone': { + 'start_order': 1, + 'image': 'quay.io/tripleo/keystone', + 'restart': 'always' + }, + }, + { + 'nova': { + 'start_order': 1, + 'image': 'quay.io/tripleo/nova', + 'action': 'exec' + }, + }, + { + 'mysql': { + 'start_order': 0, + 'image': 'quay.io/tripleo/mysql' + } + } + ] + expected_list = [ + { + 'mysql': { + 'start_order': 0, + 'image': 'quay.io/tripleo/mysql' + }, + } + ] + result = self.filters.haskey(data=data, + attribute='restart', + value='always', + reverse=True, + excluded_keys=['action']) + self.assertEqual(result, expected_list) + def test_haskey_reverse(self): data = [ {