diff --git a/plugins/modules/podman_container.py b/plugins/modules/podman_container.py index b2c79e2..a4e5422 100644 --- a/plugins/modules/podman_container.py +++ b/plugins/modules/podman_container.py @@ -531,7 +531,6 @@ options: - If true, the first argument refers to an exploded container on the file system. The default is false. type: bool - default: False security_opt: description: - Security Options. For example security_opt "seccomp=unconfined" @@ -1274,7 +1273,6 @@ class PodmanDefaults: # "memory_swappiness": -1, "no_hosts": False, # libpod issue with networks in inspection - "network": ["default"], "oom_score_adj": 0, "pid": "", "privileged": False, @@ -1597,14 +1595,26 @@ class PodmanContainerDiff: return self._diff_update_and_compare('memory_reservation', before, after) def diffparam_network(self): - before = [self.info['hostconfig']['networkmode']] - # TODO(sshnaidm): special case for rootful container > v2. - # Discover later what is running user and set default accordingly - if not self.module.params['network'] and ( - before == ['bridge'] or self.params['pod']): + net_mode_before = self.info['hostconfig']['networkmode'] + net_mode_after = '' + before = list(self.info['networksettings'].get('networks', {})) + after = self.params['network'] or [] + # If container is in pod and no networks are provided + if not self.module.params['network'] and self.params['pod']: after = before - else: - after = self.params['network'] + return self._diff_update_and_compare('network', before, after) + # Check special network modes + if after in [['bridge'], ['host'], ['slirp4netns'], ['none']]: + net_mode_after = after[0] + # If changes are only for network mode and container has no networks + if net_mode_after and not before: + # Remove differences between v1 and v2 + net_mode_after = net_mode_after.replace('bridge', 'default') + net_mode_after = net_mode_after.replace('slirp4netns', 'default') + net_mode_before = net_mode_before.replace('bridge', 'default') + net_mode_before = net_mode_before.replace('slirp4netns', 'default') + return self._diff_update_and_compare('network', net_mode_before, net_mode_after) + before, after = sorted(list(set(before))), sorted(list(set(after))) return self._diff_update_and_compare('network', before, after) def diffparam_no_hosts(self): @@ -1799,8 +1809,7 @@ class PodmanContainerDiff: if dff_func(): if fail_fast: return True - else: - different = True + different = True # Check non idempotent parameters for p in self.non_idempotent: if self.module.params[p] is not None and self.module.params[p] not in [{}, [], '']: diff --git a/tests/integration/targets/podman_container_idempotency/tasks/idem_networks.yml b/tests/integration/targets/podman_container_idempotency/tasks/idem_networks.yml new file mode 100644 index 0000000..5a21aac --- /dev/null +++ b/tests/integration/targets/podman_container_idempotency/tasks/idem_networks.yml @@ -0,0 +1,40 @@ +- name: Remove container netcontainer + containers.podman.podman_container: + name: netcontainer + state: absent + +- name: Run container with {{ item.first_net }} + containers.podman.podman_container: + name: netcontainer + image: "{{ idem_image }}" + command: 1h + state: present + network: "{{ item.first_net }}" + +- name: Run container again with {{ item.first_net }} + containers.podman.podman_container: + name: netcontainer + image: "{{ idem_image }}" + command: 1h + state: present + network: "{{ item.first_net }}" + register: info + +- name: Check info for 2 runs of {{ item.first_net }} + assert: + that: + - info is not changed + +- name: Run changed container with {{ item.next_net }} + containers.podman.podman_container: + name: netcontainer + image: "{{ idem_image }}" + command: 1h + state: present + network: "{{ item.next_net }}" + register: info1 + +- name: Check info + assert: + that: + - info1 is changed diff --git a/tests/integration/targets/podman_container_idempotency/tasks/main.yml b/tests/integration/targets/podman_container_idempotency/tasks/main.yml index 8a59be8..f5dbd4b 100644 --- a/tests/integration/targets/podman_container_idempotency/tasks/main.yml +++ b/tests/integration/targets/podman_container_idempotency/tasks/main.yml @@ -25,3 +25,12 @@ args: apply: become: true + +- name: Test idempotency for root network containers + include_tasks: root-podman-network.yml + args: + apply: + become: true + +- name: Test idempotency for root network containers + include_tasks: rootless-podman-network.yml diff --git a/tests/integration/targets/podman_container_idempotency/tasks/root-podman-network.yml b/tests/integration/targets/podman_container_idempotency/tasks/root-podman-network.yml new file mode 100644 index 0000000..bdcbd15 --- /dev/null +++ b/tests/integration/targets/podman_container_idempotency/tasks/root-podman-network.yml @@ -0,0 +1,67 @@ +- name: Test podman rootful container with networks + block: + + - name: Remove container + containers.podman.podman_container: + name: netcontainer + state: absent + + - name: Create network testnet + command: podman network create testnet --subnet 10.92.92.0/24 + + - name: Create network anothernet + command: podman network create anothernet --subnet 10.72.72.0/24 + + - name: List current networks + command: podman network ls + + - name: Set test data + set_fact: + testdata: + - first_net: host + next_net: bridge + - first_net: bridge + next_net: host + - first_net: none + next_net: host + - first_net: host + next_net: none + - first_net: anothernet + next_net: testnet + - first_net: testnet + next_net: + - testnet + - anothernet + - first_net: + - testnet + - anothernet + next_net: anothernet + - first_net: + - testnet + - anothernet + next_net: bridge + - first_net: + - testnet + - anothernet + next_net: host + - first_net: host + next_net: anothernet + - first_net: bridge + next_net: + - anothernet + - testnet + + - include_tasks: idem_networks.yml + loop: "{{ testdata }}" + + always: + + - name: Delete all pods leftovers from tests + containers.podman.podman_container: + name: netcontainer + state: absent + + - name: Delete all network leftovers from tests + shell: | + podman network rm -f anothernet + podman network rm -f testnet diff --git a/tests/integration/targets/podman_container_idempotency/tasks/rootless-podman-network.yml b/tests/integration/targets/podman_container_idempotency/tasks/rootless-podman-network.yml new file mode 100644 index 0000000..2178e52 --- /dev/null +++ b/tests/integration/targets/podman_container_idempotency/tasks/rootless-podman-network.yml @@ -0,0 +1,103 @@ +- name: Test podman rootful container with networks + block: + + - name: Remove container rootlessnet + containers.podman.podman_container: + name: rootlessnet + state: absent + + - name: Run container with no specified networks + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + + - name: Run container again with no specified networks + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + register: info + + - name: Check info for no specified networks + assert: + that: + - info is not changed + + - name: Run container with network mode host + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + network: host + register: info1 + + - name: Check info with network mode host + assert: + that: + - info1 is changed + + - name: Run container with network mode host again + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + network: host + register: info2 + + - name: Check info with network mode host again + assert: + that: + - info2 is not changed + + - name: Run container without network at all + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + network: none + register: info3 + + - name: Check info without network at all + assert: + that: + - info3 is changed + + - name: Run container without network at all again + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + network: none + register: info4 + + - name: Check info without network at all again + assert: + that: + - info4 is not changed + + - name: Run container with default network mode + containers.podman.podman_container: + name: rootlessnet + image: "{{ idem_image }}" + command: 1h + state: present + register: info5 + + - name: Check info with default network mode + assert: + that: + - info5 is changed + + always: + + - name: Delete all pods leftovers from tests + containers.podman.podman_container: + name: rootlessnet + state: absent