diff --git a/plugins/inventory/kubevirt.py b/plugins/inventory/kubevirt.py index 74db5a4..40cbc99 100644 --- a/plugins/inventory/kubevirt.py +++ b/plugins/inventory/kubevirt.py @@ -136,7 +136,6 @@ from typing import ( # potentially print a warning to the user if the client is missing. try: from kubernetes.dynamic.exceptions import DynamicApiError - from kubernetes.dynamic.resource import ResourceField HAS_K8S_MODULE_HELPER = True K8S_IMPORT_EXCEPTION = None @@ -147,17 +146,11 @@ except ImportError as e: Dummy class, mainly used for ansible-test sanity. """ - class ResourceField: - """ - Dummy class, mainly used for ansible-test sanity. - """ - HAS_K8S_MODULE_HELPER = False K8S_IMPORT_EXCEPTION = e from ansible.plugins.inventory import BaseInventoryPlugin, Constructable, Cacheable - from ansible_collections.kubernetes.core.plugins.module_utils.k8s.client import ( get_api_client, K8SClient, @@ -293,6 +286,20 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): """ return InventoryModule.snake_case_pattern.sub("_", name).lower() + @staticmethod + def obj_is_valid(obj: Dict) -> bool: + """ + obj_is_valid ensures commonly used keys are present in the passed object. + """ + return bool( + "spec" in obj + and "status" in obj + and "metadata" in obj + and obj["metadata"].get("name") + and obj["metadata"].get("namespace") + and obj["metadata"].get("uid") + ) + @staticmethod def get_host_from_service(service: Dict, node_name: Optional[str]) -> Optional[str]: """ @@ -360,9 +367,6 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): return False - def __init__(self) -> None: - super().__init__() - def verify_file(self, path: str) -> None: """ verify_file ensures the inventory file is compatible with this plugin. @@ -480,7 +484,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): def get_resources( self, client: K8SClient, api_version: str, kind: str, **kwargs - ) -> List[ResourceField]: + ) -> List[Dict]: """ get_resources uses a dynamic K8SClient to fetch resources from the K8S API. """ @@ -493,7 +497,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): f"Error fetching {kind} list: {self.format_dynamic_api_exc(exc)}" ) from exc - return result.items + return [item.to_dict() for item in result.items] def get_available_namespaces(self, client: K8SClient) -> List[str]: """ @@ -501,13 +505,14 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): configured credentials and returns them. """ return [ - namespace.metadata.name + namespace["metadata"]["name"] for namespace in self.get_resources(client, "v1", "Namespace") + if "metadata" in namespace and "name" in namespace["metadata"] ] def get_vms_for_namespace( self, client: K8SClient, namespace: str, opts: InventoryOptions - ) -> List[ResourceField]: + ) -> List[Dict]: """ get_vms_for_namespace returns a list of all VirtualMachines in a namespace. """ @@ -521,7 +526,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): def get_vmis_for_namespace( self, client: K8SClient, namespace: str, opts: InventoryOptions - ) -> List[ResourceField]: + ) -> List[Dict]: """ get_vmis_for_namespace returns a list of all VirtualMachineInstances in a namespace. """ @@ -538,7 +543,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): get_ssh_services_for_namespace retrieves all services of a namespace exposing port 22/ssh. The services are mapped to the name of the corresponding domain. """ - service_list = self.get_resources( + items = self.get_resources( client, "v1", "Service", @@ -546,12 +551,12 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): ) services = {} - for service in service_list: + for service in items: # Continue if service is not of type LoadBalancer or NodePort - if service.get("spec") is None: + if not (spec := service.get("spec")): continue - if service["spec"].get("type") not in ( + if spec.get("type") not in ( TYPE_LOADBALANCER, TYPE_NODEPORT, ): @@ -559,17 +564,20 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): # Continue if ports are not defined, there are more than one port mapping # or the target port is not port 22/ssh - ports = service["spec"].get("ports") - if ports is None or len(ports) != 1 or ports[0].get("targetPort") != 22: + if ( + (ports := spec.get("ports")) is None + or len(ports) != 1 + or ports[0].get("targetPort") != 22 + ): continue # Only add the service to the dict if the domain selector is present - domain = service["spec"].get("selector", {}).get(LABEL_KUBEVIRT_IO_DOMAIN) - if domain is not None: + if domain := spec.get("selector", {}).get(LABEL_KUBEVIRT_IO_DOMAIN): services[domain] = service return services + def populate_inventory_from_namespace( self, client: K8SClient, name: str, namespace: str, opts: InventoryOptions ) -> None: @@ -578,12 +586,14 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): namespace to the inventory. """ vms = { - vm.metadata.name: vm + vm["metadata"]["name"]: vm for vm in self.get_vms_for_namespace(client, namespace, opts) + if self.obj_is_valid(vm) } vmis = { - vmi.metadata.name: vmi + vmi["metadata"]["name"]: vmi for vmi in self.get_vmis_for_namespace(client, namespace, opts) + if self.obj_is_valid(vmi) } if not vms and not vmis: @@ -601,7 +611,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): # Add found VMs and optionally enhance with VMI data for name, vm in vms.items(): - hostname = self.add_host(vm, opts.host_format, namespace_group) + hostname = self.add_host(vm["metadata"], opts.host_format, namespace_group) self.set_vars_from_vm(hostname, vm, opts) if name in vmis: self.set_vars_from_vmi(hostname, vmis[name], services, opts) @@ -611,36 +621,32 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): for name, vmi in vmis.items(): if name in vms: continue - hostname = self.add_host(vmi, opts.host_format, namespace_group) + hostname = self.add_host(vmi["metadata"], opts.host_format, namespace_group) self.set_vars_from_vmi(hostname, vmi, services, opts) self.set_composable_vars(hostname) - def add_host( - self, obj: ResourceField, host_format: str, namespace_group: str - ) -> str: + def add_host(self, metadata: Dict, host_format: str, namespace_group: str) -> str: """ add_hosts adds a host to the inventory. """ hostname = host_format.format( - namespace=obj.metadata.namespace, - name=obj.metadata.name, - uid=obj.metadata.uid, + namespace=metadata["namespace"], + name=metadata["name"], + uid=metadata["uid"], ) self.inventory.add_host(hostname) self.inventory.add_child(namespace_group, hostname) return hostname - def set_vars_from_vm( - self, hostname: str, vm: ResourceField, opts: InventoryOptions - ) -> None: + def set_vars_from_vm(self, hostname: str, vm: Dict, opts: InventoryOptions) -> None: """ set_vars_from_vm sets inventory variables from a VM prefixed with vm_. """ self.set_common_vars(hostname, "vm", vm, opts) def set_vars_from_vmi( - self, hostname: str, vmi: ResourceField, services: Dict, opts: InventoryOptions + self, hostname: str, vmi: Dict, services: Dict, opts: InventoryOptions ) -> None: """ set_vars_from_vmi sets inventory variables from a VMI prefixed with vmi_ and @@ -648,76 +654,76 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): """ self.set_common_vars(hostname, "vmi", vmi, opts) + if not (interfaces := vmi["status"].get("interfaces")): + return + if opts.network_name is None: # Use first interface - interface = vmi.status.interfaces[0] if vmi.status.interfaces else None + interface = interfaces[0] else: # Find interface by its name interface = next( - (i for i in vmi.status.interfaces if i.name == opts.network_name), + (i for i in interfaces if i.get("name") == opts.network_name), None, ) # If interface is not found or IP address is not reported skip this VMI - if interface is None or interface.ipAddress is None: + if not interface or not interface.get("ipAddress"): return # Set up the connection service = None if self.is_windows( - {} if not vmi.status.guestOSInfo else vmi.status.guestOSInfo.to_dict(), - {} if not vmi.metadata.annotations else vmi.metadata.annotations.to_dict(), + vmi["status"].get("guestOSInfo", {}), + vmi["metadata"].get("annotations", {}), ): self.inventory.set_variable(hostname, "ansible_connection", "winrm") else: - service = services.get(vmi.metadata.labels.get(LABEL_KUBEVIRT_IO_DOMAIN)) + service = services.get( + vmi["metadata"].get("labels", {}).get(LABEL_KUBEVIRT_IO_DOMAIN) + ) self.set_ansible_host_and_port( vmi, hostname, - interface.ipAddress, + interface["ipAddress"], service, opts, ) def set_common_vars( - self, hostname: str, prefix: str, obj: ResourceField, opts: InventoryOptions + self, hostname: str, prefix: str, obj: Dict, opts: InventoryOptions ): """ set_common_vars sets common inventory variables from VMs or VMIs. """ # Add hostvars from metadata - if metadata := obj.metadata: - if metadata.annotations: - self.inventory.set_variable( - hostname, f"{prefix}_annotations", metadata.annotations.to_dict() - ) - if metadata.labels: - self.inventory.set_variable( - hostname, f"{prefix}_labels", metadata.labels.to_dict() - ) - # Create label groups and add vm to it if enabled - if opts.create_groups: - self.set_groups_from_labels(hostname, metadata.labels) - if metadata.resourceVersion: - self.inventory.set_variable( - hostname, f"{prefix}_resource_version", metadata.resourceVersion - ) - if metadata.uid: - self.inventory.set_variable(hostname, f"{prefix}_uid", metadata.uid) + if annotations := obj["metadata"].get("annotations"): + self.inventory.set_variable(hostname, f"{prefix}_annotations", annotations) + if labels := obj["metadata"].get("labels"): + self.inventory.set_variable(hostname, f"{prefix}_labels", labels) + # Create label groups and add vm to it if enabled + if opts.create_groups: + self.set_groups_from_labels(hostname, labels) + if resource_version := obj["metadata"].get("resourceVersion"): + self.inventory.set_variable( + hostname, f"{prefix}_resource_version", resource_version + ) + if uid := obj["metadata"].get("uid"): + self.inventory.set_variable(hostname, f"{prefix}_uid", uid) # Add hostvars from status - if obj.status: - for key, value in obj.status.to_dict().items(): - name = self.format_var_name(key) - self.inventory.set_variable(hostname, f"{prefix}_{name}", value) + for key, value in obj["status"].items(): + self.inventory.set_variable( + hostname, f"{prefix}_{self.format_var_name(key)}", value + ) - def set_groups_from_labels(self, hostname: str, labels: ResourceField) -> None: + def set_groups_from_labels(self, hostname: str, labels: Dict) -> None: """ set_groups_from_labels adds groups for each label of a VM or VMI and adds the host to each group. """ groups = [] - for key, value in labels.to_dict().items(): + for key, value in labels.items(): group_name = self._sanitize_group_name(f"label_{key}_{value}") if group_name not in groups: groups.append(group_name) @@ -728,7 +734,7 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): def set_ansible_host_and_port( self, - vmi: ResourceField, + vmi: Dict, hostname: str, ip_address: str, service: Optional[Dict], @@ -743,15 +749,13 @@ class InventoryModule(BaseInventoryPlugin, Constructable, Cacheable): if opts.kube_secondary_dns and opts.network_name: # Set ansible_host to the kubesecondarydns derived host name if enabled # See https://github.com/kubevirt/kubesecondarydns#parameters - ansible_host = ( - f"{opts.network_name}.{vmi.metadata.name}.{vmi.metadata.namespace}.vm" - ) + ansible_host = f"{opts.network_name}.{vmi['metadata']['name']}.{vmi['metadata']['namespace']}.vm" if opts.base_domain: ansible_host += f".{opts.base_domain}" elif opts.use_service and service and not opts.network_name: # Set ansible_host and ansible_port to the host and port from the LoadBalancer # or NodePort service exposing SSH - node_name = vmi.status.nodeName + node_name = vmi["status"].get("nodeName") if node_name and opts.append_base_domain and opts.base_domain: node_name += f".{opts.base_domain}" host = self.get_host_from_service(service, node_name) diff --git a/tests/unit/plugins/inventory/blackbox/test_kubevirt_ansible_connection_winrm.py b/tests/unit/plugins/inventory/blackbox/test_kubevirt_ansible_connection_winrm.py index 22cc9c8..2c232ff 100644 --- a/tests/unit/plugins/inventory/blackbox/test_kubevirt_ansible_connection_winrm.py +++ b/tests/unit/plugins/inventory/blackbox/test_kubevirt_ansible_connection_winrm.py @@ -22,7 +22,9 @@ BASE_VMI = { "metadata": { "name": "testvmi", "namespace": "default", + "uid": "e86c603c-fb13-4933-bf67-de100bdba0c3", }, + "spec": {}, "status": { "interfaces": [{"ipAddress": "10.10.10.10"}], }, diff --git a/tests/unit/plugins/inventory/blackbox/test_kubevirt_set_composable_vars.py b/tests/unit/plugins/inventory/blackbox/test_kubevirt_set_composable_vars.py index 01bf367..36be197 100644 --- a/tests/unit/plugins/inventory/blackbox/test_kubevirt_set_composable_vars.py +++ b/tests/unit/plugins/inventory/blackbox/test_kubevirt_set_composable_vars.py @@ -21,7 +21,9 @@ VMI = { "metadata": { "name": "testvmi", "namespace": "default", + "uid": "6ffdef43-6c39-4441-a088-82d319ea5c13", }, + "spec": {}, "status": { "interfaces": [{"ipAddress": "10.10.10.10"}], "migrationMethod": "BlockMigration", diff --git a/tests/unit/plugins/inventory/blackbox/test_kubevirt_stopped_vm.py b/tests/unit/plugins/inventory/blackbox/test_kubevirt_stopped_vm.py index 04d4c9d..1b7a93a 100644 --- a/tests/unit/plugins/inventory/blackbox/test_kubevirt_stopped_vm.py +++ b/tests/unit/plugins/inventory/blackbox/test_kubevirt_stopped_vm.py @@ -24,6 +24,7 @@ VM1 = { "uid": "940003aa-0160-4b7e-9e55-8ec3df72047f", }, "spec": {"running": True}, + "status": {}, } VM2 = { @@ -33,6 +34,7 @@ VM2 = { "uid": "c2c68de5-b9d7-4c25-872f-462e7245b3e6", }, "spec": {"running": False}, + "status": {}, } VMI1 = { @@ -41,6 +43,7 @@ VMI1 = { "namespace": "default", "uid": "a84319a9-db31-4a36-9b66-3e387578f871", }, + "spec": {}, "status": { "interfaces": [{"ipAddress": "10.10.10.10"}], }, diff --git a/tests/unit/plugins/inventory/test_kubevirt.py b/tests/unit/plugins/inventory/test_kubevirt.py index ed28731..befa273 100644 --- a/tests/unit/plugins/inventory/test_kubevirt.py +++ b/tests/unit/plugins/inventory/test_kubevirt.py @@ -8,8 +8,6 @@ __metaclass__ = type import pytest -from addict import Dict - from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( InventoryModule, ) @@ -48,6 +46,55 @@ def test_format_var_name(name, expected): assert InventoryModule.format_var_name(name) == expected +@pytest.mark.parametrize( + "obj,expected", + [ + ({}, False), + ({"spec": {}}, False), + ({"status": {}}, False), + ({"metadata": {}}, False), + ({"spec": {}, "status": {}}, False), + ({"spec": {}, "metadata": {}}, False), + ({"status": {}, "metadata": {}}, False), + ({"spec": {}, "status": {}, "metadata": {}}, False), + ({"spec": {}, "status": {}, "metadata": {}, "something": {}}, False), + ({"spec": {}, "status": {}, "metadata": {"name": "test"}}, False), + ({"spec": {}, "status": {}, "metadata": {"namespace": "test"}}, False), + ({"spec": {}, "status": {}, "metadata": {"uid": "test"}}, False), + ( + { + "spec": {}, + "status": {}, + "metadata": {"name": "test", "namespace": "test"}, + }, + False, + ), + ( + { + "spec": {}, + "status": {}, + "metadata": {"name": "test", "namespace": "test", "something": "test"}, + }, + False, + ), + ( + {"spec": {}, "status": {}, "metadata": {"name": "test", "uid": "test"}}, + False, + ), + ( + { + "spec": {}, + "status": {}, + "metadata": {"name": "test", "namespace": "test", "uid": "test"}, + }, + True, + ), + ], +) +def test_obj_is_valid(obj, expected): + assert InventoryModule.obj_is_valid(obj) == expected + + @pytest.mark.parametrize( "service,node_name,expected", [ @@ -223,7 +270,7 @@ def test_get_cluster_domain(inventory, client): ) def test_set_groups_from_labels(inventory, groups, labels, expected): hostname = "default-testvm" - inventory.set_groups_from_labels(hostname, Dict(labels)) + inventory.set_groups_from_labels(hostname, labels) for group in expected: assert group in groups assert hostname in groups[group]["children"] diff --git a/tests/unit/plugins/inventory/test_kubevirt_add_host.py b/tests/unit/plugins/inventory/test_kubevirt_add_host.py index fd1cb97..fd774e1 100644 --- a/tests/unit/plugins/inventory/test_kubevirt_add_host.py +++ b/tests/unit/plugins/inventory/test_kubevirt_add_host.py @@ -8,8 +8,6 @@ __metaclass__ = type import pytest -from addict import Dict - from ansible_collections.kubevirt.core.tests.unit.plugins.inventory.constants import ( DEFAULT_NAMESPACE, ) @@ -65,15 +63,11 @@ def test_add_host(inventory, groups, hosts, host_format, expected): inventory.inventory.add_group(namespace_group) inventory.add_host( - Dict( - { - "metadata": { - "name": "testvm", - "namespace": DEFAULT_NAMESPACE, - "uid": "f8abae7c-d792-4b9b-af95-62d322ae5bc1", - } - } - ), + { + "name": "testvm", + "namespace": DEFAULT_NAMESPACE, + "uid": "f8abae7c-d792-4b9b-af95-62d322ae5bc1", + }, host_format, namespace_group, ) diff --git a/tests/unit/plugins/inventory/test_kubevirt_populate_inventory_from_namespace.py b/tests/unit/plugins/inventory/test_kubevirt_populate_inventory_from_namespace.py index 1077a39..c368064 100644 --- a/tests/unit/plugins/inventory/test_kubevirt_populate_inventory_from_namespace.py +++ b/tests/unit/plugins/inventory/test_kubevirt_populate_inventory_from_namespace.py @@ -8,9 +8,6 @@ __metaclass__ = type import pytest -from addict import Dict - - from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( InventoryOptions, ) @@ -25,6 +22,8 @@ VM1 = { "namespace": DEFAULT_NAMESPACE, "uid": "940003aa-0160-4b7e-9e55-8ec3df72047f", }, + "spec": {}, + "status": {}, } VM2 = { @@ -33,6 +32,8 @@ VM2 = { "namespace": DEFAULT_NAMESPACE, "uid": "c2c68de5-b9d7-4c25-872f-462e7245b3e6", }, + "spec": {}, + "status": {}, } VMI1 = { @@ -41,6 +42,7 @@ VMI1 = { "namespace": DEFAULT_NAMESPACE, "uid": "a84319a9-db31-4a36-9b66-3e387578f871", }, + "spec": {}, "status": { "interfaces": [{"ipAddress": "10.10.10.10"}], }, @@ -52,6 +54,7 @@ VMI2 = { "namespace": DEFAULT_NAMESPACE, "uid": "fd35700a-9cbe-488b-8f32-7adbe57eadc2", }, + "spec": {}, "status": { "interfaces": [{"ipAddress": "10.10.10.10"}], }, @@ -78,20 +81,20 @@ VMI2 = { def test_populate_inventory_from_namespace( mocker, inventory, groups, vms, vmis, expected ): - _vms = {vm["metadata"]["name"]: Dict(vm) for vm in vms} - _vmis = {vmi["metadata"]["name"]: Dict(vmi) for vmi in vmis} + _vms = {vm["metadata"]["name"]: vm for vm in vms} + _vmis = {vmi["metadata"]["name"]: vmi for vmi in vmis} opts = InventoryOptions() def format_hostname(obj): return opts.host_format.format( - namespace=obj.metadata.namespace, - name=obj.metadata.name, - uid=obj.metadata.uid, + namespace=obj["metadata"]["namespace"], + name=obj["metadata"]["name"], + uid=obj["metadata"]["uid"], ) def add_host_call(obj): return mocker.call( - obj, + obj["metadata"], opts.host_format, f"namespace_{DEFAULT_NAMESPACE}", ) diff --git a/tests/unit/plugins/inventory/test_kubevirt_set_ansible_host_and_port.py b/tests/unit/plugins/inventory/test_kubevirt_set_ansible_host_and_port.py index ab20265..5550167 100644 --- a/tests/unit/plugins/inventory/test_kubevirt_set_ansible_host_and_port.py +++ b/tests/unit/plugins/inventory/test_kubevirt_set_ansible_host_and_port.py @@ -8,8 +8,6 @@ __metaclass__ = type import pytest -from addict import Dict - from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( InventoryOptions, ) @@ -29,7 +27,7 @@ def test_use_ip_address_by_default(mocker, inventory, opts): hostname = "default-testvm" ip_address = "1.1.1.1" - inventory.set_ansible_host_and_port(Dict(), hostname, ip_address, None, opts) + inventory.set_ansible_host_and_port({}, hostname, ip_address, None, opts) set_variable.assert_has_calls( [ @@ -50,12 +48,10 @@ def test_kube_secondary_dns(mocker, inventory, base_domain): set_variable = mocker.patch.object(inventory.inventory, "set_variable") hostname = "default-testvm" - vmi = Dict( - { - "metadata": {"name": "testvm", "namespace": "default"}, - "status": {"interfaces": [{"name": "awesome"}]}, - } - ) + vmi = { + "metadata": {"name": "testvm", "namespace": "default"}, + "status": {"interfaces": [{"name": "awesome"}]}, + } inventory.set_ansible_host_and_port( vmi, @@ -85,12 +81,10 @@ def test_kube_secondary_dns_precedence_over_service(mocker, inventory): set_variable = mocker.patch.object(inventory.inventory, "set_variable") hostname = "default-testvm" - vmi = Dict( - { - "metadata": {"name": "testvm", "namespace": "default"}, - "status": {"interfaces": [{"name": "awesome"}]}, - } - ) + vmi = { + "metadata": {"name": "testvm", "namespace": "default"}, + "status": {"interfaces": [{"name": "awesome"}]}, + } inventory.set_ansible_host_and_port( vmi, @@ -170,13 +164,11 @@ def test_service(mocker, inventory, service, expected_host, expected_port): set_variable = mocker.patch.object(inventory.inventory, "set_variable") hostname = "default-testvm" - vmi = Dict( - { - "status": { - "nodeName": "testnode.example.com", - }, - } - ) + vmi = { + "status": { + "nodeName": "testnode.example.com", + }, + } inventory.set_ansible_host_and_port( vmi, @@ -198,13 +190,11 @@ def test_service_append_base_domain(mocker, inventory): set_variable = mocker.patch.object(inventory.inventory, "set_variable") hostname = "default-testvm" - vmi = Dict( - { - "status": { - "nodeName": "testnode", - }, - } - ) + vmi = { + "status": { + "nodeName": "testnode", + }, + } service = { "spec": { "type": "NodePort", @@ -243,13 +233,11 @@ def test_service_fallback(mocker, inventory, host, port): mocker.patch.object(inventory, "get_port_from_service", return_value=port) hostname = "default-testvm" - vmi = Dict( - { - "status": { - "nodeName": "testnode", - }, - } - ) + vmi = { + "status": { + "nodeName": "testnode", + }, + } inventory.set_ansible_host_and_port( vmi, hostname, @@ -271,7 +259,7 @@ def test_no_service_if_network_name(mocker, inventory): hostname = "default-testvm" inventory.set_ansible_host_and_port( - Dict(), + {}, hostname, "1.2.3.4", {"something": "something"}, diff --git a/tests/unit/plugins/inventory/test_kubevirt_set_common_vars.py b/tests/unit/plugins/inventory/test_kubevirt_set_common_vars.py index 6e76032..0085b83 100644 --- a/tests/unit/plugins/inventory/test_kubevirt_set_common_vars.py +++ b/tests/unit/plugins/inventory/test_kubevirt_set_common_vars.py @@ -11,8 +11,6 @@ from string import ascii_lowercase import pytest -from addict import Dict - from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( InventoryOptions, ) @@ -26,6 +24,8 @@ from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( "metadata": { "something": "idontcare", }, + "spec": {}, + "status": {}, }, {}, ), @@ -34,6 +34,8 @@ from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( "metadata": { "annotations": {"testanno": "testval"}, }, + "spec": {}, + "status": {}, }, {"annotations": {"testanno": "testval"}}, ), @@ -42,6 +44,8 @@ from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( "metadata": { "labels": {"testlabel": "testval"}, }, + "spec": {}, + "status": {}, }, {"labels": {"testlabel": "testval"}}, ), @@ -50,6 +54,8 @@ from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( "metadata": { "resourceVersion": "123", }, + "spec": {}, + "status": {}, }, {"resource_version": "123"}, ), @@ -58,11 +64,15 @@ from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( "metadata": { "uid": "48e6ed2c-d8a2-4172-844d-0fe7056aa180", }, + "spec": {}, + "status": {}, }, {"uid": "48e6ed2c-d8a2-4172-844d-0fe7056aa180"}, ), ( { + "metadata": {}, + "spec": {}, "status": { "interfaces": [{"ipAddress": "10.10.10.10"}], }, @@ -75,7 +85,7 @@ def test_set_common_vars(inventory, hosts, obj, expected): hostname = "default-testvm" prefix = "".join(choice(ascii_lowercase) for i in range(5)) inventory.inventory.add_host(hostname) - inventory.set_common_vars(hostname, prefix, Dict(obj), InventoryOptions()) + inventory.set_common_vars(hostname, prefix, obj, InventoryOptions()) for key, value in expected.items(): prefixed_key = f"{prefix}_{key}" @@ -99,7 +109,7 @@ def test_set_common_vars_create_groups(mocker, inventory, create_groups): opts = InventoryOptions(create_groups=create_groups) inventory.set_common_vars( - hostname, "prefix", Dict({"metadata": {"labels": labels}}), opts + hostname, "prefix", {"metadata": {"labels": labels}, "status": {}}, opts ) if create_groups: @@ -111,12 +121,16 @@ def test_set_common_vars_create_groups(mocker, inventory, create_groups): def test_called_by_set_vars_from(mocker, inventory): hostname = "default-testvm" opts = InventoryOptions() + obj = {"status": {}} set_common_vars = mocker.patch.object(inventory, "set_common_vars") - inventory.set_vars_from_vm(hostname, Dict(), opts) - inventory.set_vars_from_vmi(hostname, Dict(), {}, opts) + inventory.set_vars_from_vm(hostname, obj, opts) + inventory.set_vars_from_vmi(hostname, obj, {}, opts) set_common_vars.assert_has_calls( - [mocker.call(hostname, "vm", {}, opts), mocker.call(hostname, "vmi", {}, opts)] + [ + mocker.call(hostname, "vm", obj, opts), + mocker.call(hostname, "vmi", obj, opts), + ] ) diff --git a/tests/unit/plugins/inventory/test_kubevirt_set_vars_from_vmi.py b/tests/unit/plugins/inventory/test_kubevirt_set_vars_from_vmi.py index db7dc1f..917a9c2 100644 --- a/tests/unit/plugins/inventory/test_kubevirt_set_vars_from_vmi.py +++ b/tests/unit/plugins/inventory/test_kubevirt_set_vars_from_vmi.py @@ -6,8 +6,6 @@ from __future__ import absolute_import, division, print_function __metaclass__ = type -from addict import Dict - from ansible_collections.kubevirt.core.plugins.inventory.kubevirt import ( InventoryOptions, LABEL_KUBEVIRT_IO_DOMAIN, @@ -20,7 +18,7 @@ def test_ignore_vmi_without_interface(mocker, inventory): inventory, "set_ansible_host_and_port" ) - vmi = Dict({"status": {}}) + vmi = {"status": {}} inventory.set_vars_from_vmi("default-testvm", vmi, {}, InventoryOptions()) set_ansible_host_and_port.assert_not_called() @@ -33,9 +31,10 @@ def test_use_first_interface_by_default(mocker, inventory): ) hostname = "default-testvm" - vmi = Dict( - {"status": {"interfaces": [{"ipAddress": "1.1.1.1"}, {"ipAddress": "2.2.2.2"}]}} - ) + vmi = { + "metadata": {}, + "status": {"interfaces": [{"ipAddress": "1.1.1.1"}, {"ipAddress": "2.2.2.2"}]}, + } opts = InventoryOptions() inventory.set_vars_from_vmi(hostname, vmi, {}, opts) @@ -51,16 +50,15 @@ def test_use_named_interface(mocker, inventory): ) hostname = "default-testvm" - vmi = Dict( - { - "status": { - "interfaces": [ - {"name": "first", "ipAddress": "1.1.1.1"}, - {"name": "second", "ipAddress": "2.2.2.2"}, - ] - } - } - ) + vmi = { + "metadata": {}, + "status": { + "interfaces": [ + {"name": "first", "ipAddress": "1.1.1.1"}, + {"name": "second", "ipAddress": "2.2.2.2"}, + ] + }, + } opts = InventoryOptions(network_name="second") inventory.set_vars_from_vmi(hostname, vmi, {}, opts) @@ -75,9 +73,10 @@ def test_ignore_vmi_without_named_interface(mocker, inventory): inventory, "set_ansible_host_and_port" ) - vmi = Dict( - {"status": {"interfaces": [{"name": "somename", "ipAddress": "1.1.1.1"}]}} - ) + vmi = { + "metadata": {}, + "status": {"interfaces": [{"name": "somename", "ipAddress": "1.1.1.1"}]}, + } inventory.set_vars_from_vmi( "default-testvm", vmi, {}, InventoryOptions(network_name="awesome") ) @@ -92,7 +91,7 @@ def test_set_winrm_if_windows(mocker, inventory): set_variable = mocker.patch.object(inventory.inventory, "set_variable") hostname = "default-testvm" - vmi = Dict({"status": {"interfaces": [{"ipAddress": "1.1.1.1"}]}}) + vmi = {"metadata": {}, "status": {"interfaces": [{"ipAddress": "1.1.1.1"}]}} inventory.set_vars_from_vmi(hostname, vmi, {}, InventoryOptions()) set_variable.assert_called_once_with(hostname, "ansible_connection", "winrm") @@ -105,12 +104,10 @@ def test_service_lookup(mocker, inventory): ) hostname = "default-testvm" - vmi = Dict( - { - "metadata": {"labels": {LABEL_KUBEVIRT_IO_DOMAIN: "testdomain"}}, - "status": {"interfaces": [{"name": "somename", "ipAddress": "1.1.1.1"}]}, - } - ) + vmi = { + "metadata": {"labels": {LABEL_KUBEVIRT_IO_DOMAIN: "testdomain"}}, + "status": {"interfaces": [{"name": "somename", "ipAddress": "1.1.1.1"}]}, + } opts = InventoryOptions() service = {"metadata": {"name": "testsvc"}} inventory.set_vars_from_vmi(hostname, vmi, {"testdomain": service}, opts)