Ovirt vms improve (#20882)

* cloud: ovirt: add function to get id by name

* cloud: ovirt: add instance type parameter

* cloud: ovirt: use param method instead of module.params

* cloud: ovirt: use 'and' at begging of next line

* cloud: ovirt: add description parameter to vms module

* cloud: ovirt: add comment parameter to vms module

* cloud: ovirt: add timezone parameter to vms module

* cloud: ovirt: add serial_policy parameter to vms module
This commit is contained in:
Ondra Machacek 2017-02-02 19:51:26 +01:00 committed by Ryan Brown
parent ee7f1cde0e
commit 4269b12c9d
3 changed files with 143 additions and 48 deletions

View file

@ -190,7 +190,7 @@ def get_link_name(connection, link):
return None return None
def equal(param1, param2): def equal(param1, param2, ignore_case=False):
""" """
Compare two parameters and return if they are equal. Compare two parameters and return if they are equal.
This parameter doesn't run equal operation if first parameter is None. This parameter doesn't run equal operation if first parameter is None.
@ -202,6 +202,8 @@ def equal(param1, param2):
:return: True if parameters are equal or first parameter is None, otherwise False :return: True if parameters are equal or first parameter is None, otherwise False
""" """
if param1 is not None: if param1 is not None:
if ignore_case:
return param1.lower() == param2.lower()
return param1 == param2 return param1 == param2
return True return True
@ -271,6 +273,19 @@ def get_entity(service):
return entity return entity
def get_id_by_name(service, name, raise_error=True, ignore_case=False):
"""
Search an entity ID by it's name.
"""
entity = search_by_name(service, name)
if entity is not None:
return entity.id
if raise_error:
raise Exception("Entity '%s' was not found." % name)
def wait( def wait(
service, service,
condition, condition,

View file

@ -36,6 +36,7 @@ from ansible.module_utils.ovirt import (
equal, equal,
get_entity, get_entity,
get_link_name, get_link_name,
get_id_by_name,
ovirt_full_argument_spec, ovirt_full_argument_spec,
search_by_name, search_by_name,
wait, wait,
@ -247,6 +248,37 @@ options:
description: description:
- "Kernel command line parameters (formatted as string) to be used with the kernel specified by C(kernel_path) option." - "Kernel command line parameters (formatted as string) to be used with the kernel specified by C(kernel_path) option."
version_added: "2.3" version_added: "2.3"
instance_type:
description:
- "Name of virtual machine's hardware configuration."
- "By default no instance type is used."
version_added: "2.3"
description:
description:
- "Description of the Virtual Machine."
version_added: "2.3"
comment:
description:
- "Comment of the Virtual Machine."
version_added: "2.3"
timezone:
description:
- "Sets time zone offset of the guest hardware clock."
- "For example: Etc/GMT"
version_added: "2.3"
serial_policy:
description:
- "Specify a serial number policy for the Virtual Machine."
- "Following options are supported:"
- "C(vm) - Sets the Virtual Machine's UUID as its serial number."
- "C(host) - Sets the host's UUID as the Virtual Machine's serial number."
- "C(custom) - Allows you to specify a custom serial number in C(serial_policy_value)."
version_added: "2.3"
serial_policy_value:
description:
- "Allows you to specify a custom serial number."
- "This parameter is used only when C(serial_policy) is I(custom)."
version_added: "2.3"
notes: notes:
- "If VM is in I(UNASSIGNED) or I(UNKNOWN) state before any operation, the module will fail. - "If VM is in I(UNASSIGNED) or I(UNKNOWN) state before any operation, the module will fail.
If VM is in I(IMAGE_LOCKED) state before any operation, we try to wait for VM to be I(DOWN). If VM is in I(IMAGE_LOCKED) state before any operation, we try to wait for VM to be I(DOWN).
@ -432,13 +464,13 @@ class VmsModule(BaseModule):
through it's version until we find the version we look for. through it's version until we find the version we look for.
""" """
template = None template = None
if self._module.params['template']: if self.param('template'):
templates_service = self._connection.system_service().templates_service() templates_service = self._connection.system_service().templates_service()
templates = templates_service.list(search='name=%s' % self._module.params['template']) templates = templates_service.list(search='name=%s' % self.param('template'))
if self._module.params['template_version']: if self.param('template_version'):
templates = [ templates = [
t for t in templates t for t in templates
if t.version.version_number == self._module.params['template_version'] if t.version.version_number == self.param('template_version')
] ]
if templates: if templates:
template = templates[0] template = templates[0]
@ -448,70 +480,94 @@ class VmsModule(BaseModule):
def build_entity(self): def build_entity(self):
template = self.__get_template_with_version() template = self.__get_template_with_version()
return otypes.Vm( return otypes.Vm(
name=self._module.params['name'], name=self.param('name'),
cluster=otypes.Cluster( cluster=otypes.Cluster(
name=self._module.params['cluster'] name=self.param('cluster')
) if self._module.params['cluster'] else None, ) if self.param('cluster') else None,
template=otypes.Template( template=otypes.Template(
id=template.id, id=template.id,
) if template else None, ) if template else None,
use_latest_template_version=self._module.params['use_latest_template_version'], use_latest_template_version=self.param('use_latest_template_version'),
stateless=self._module.params['stateless'] or self._module.params['use_latest_template_version'], stateless=self.param('stateless') or self.param('use_latest_template_version'),
delete_protected=self._module.params['delete_protected'], delete_protected=self.param('delete_protected'),
high_availability=otypes.HighAvailability( high_availability=otypes.HighAvailability(
enabled=self._module.params['high_availability'] enabled=self.param('high_availability')
) if self._module.params['high_availability'] is not None else None, ) if self.param('high_availability') is not None else None,
cpu=otypes.Cpu( cpu=otypes.Cpu(
topology=otypes.CpuTopology( topology=otypes.CpuTopology(
cores=self._module.params['cpu_cores'], cores=self.param('cpu_cores'),
sockets=self._module.params['cpu_sockets'], sockets=self.param('cpu_sockets'),
) )
) if ( ) if (
self._module.params['cpu_cores'] or self._module.params['cpu_sockets'] self.param('cpu_cores') or self.param('cpu_sockets')
) else None, ) else None,
cpu_shares=self._module.params['cpu_shares'], cpu_shares=self.param('cpu_shares'),
os=otypes.OperatingSystem( os=otypes.OperatingSystem(
type=self._module.params['operating_system'], type=self.param('operating_system'),
boot=otypes.Boot( boot=otypes.Boot(
devices=[ devices=[
otypes.BootDevice(dev) for dev in self._module.params['boot_devices'] otypes.BootDevice(dev) for dev in self.param('boot_devices')
], ],
) if self._module.params['boot_devices'] else None, ) if self.param('boot_devices') else None,
) if ( ) if (
self._module.params['operating_system'] or self._module.params['boot_devices'] self.param('operating_system') or self.param('boot_devices')
) else None, ) else None,
type=otypes.VmType( type=otypes.VmType(
self._module.params['type'] self.param('type')
) if self._module.params['type'] else None, ) if self.param('type') else None,
memory=convert_to_bytes( memory=convert_to_bytes(
self._module.params['memory'] self.param('memory')
) if self._module.params['memory'] else None, ) if self.param('memory') else None,
memory_policy=otypes.MemoryPolicy( memory_policy=otypes.MemoryPolicy(
guaranteed=convert_to_bytes(self._module.params['memory_guaranteed']), guaranteed=convert_to_bytes(self.param('memory_guaranteed')),
) if self._module.params['memory_guaranteed'] else None, ) if self.param('memory_guaranteed') else None,
instance_type=otypes.InstanceType(
id=get_id_by_name(
self._connection.system_service().instance_types_service(),
self.param('instance_type'),
),
) if self.param('instance_type') else None,
description=self.param('description'),
comment=self.param('comment'),
time_zone=otypes.TimeZone(
name=self.param('timezone'),
) if self.param('timezone') else None,
serial_number=otypes.SerialNumber(
policy=otypes.SerialNumberPolicy(self.param('serial_policy')),
value=self.param('serial_policy_value'),
) if (
self.param('serial_policy') is not None or
self.param('serial_policy_value') is not None
) else None,
) )
def update_check(self, entity): def update_check(self, entity):
return ( return (
equal(self._module.params.get('cluster'), get_link_name(self._connection, entity.cluster)) and equal(self.param('cluster'), get_link_name(self._connection, entity.cluster))
equal(convert_to_bytes(self._module.params['memory']), entity.memory) and and equal(convert_to_bytes(self.param('memory')), entity.memory)
equal(convert_to_bytes(self._module.params['memory_guaranteed']), entity.memory_policy.guaranteed) and and equal(convert_to_bytes(self.param('memory_guaranteed')), entity.memory_policy.guaranteed)
equal(self._module.params.get('cpu_cores'), entity.cpu.topology.cores) and and equal(self.param('cpu_cores'), entity.cpu.topology.cores)
equal(self._module.params.get('cpu_sockets'), entity.cpu.topology.sockets) and and equal(self.param('cpu_sockets'), entity.cpu.topology.sockets)
equal(self._module.params.get('type'), str(entity.type)) and and equal(self.param('type'), str(entity.type))
equal(self._module.params.get('operating_system'), str(entity.os.type)) and and equal(self.param('operating_system'), str(entity.os.type))
equal(self._module.params.get('high_availability'), entity.high_availability.enabled) and and equal(self.param('high_availability'), entity.high_availability.enabled)
equal(self._module.params.get('stateless'), entity.stateless) and and equal(self.param('stateless'), entity.stateless)
equal(self._module.params.get('cpu_shares'), entity.cpu_shares) and and equal(self.param('cpu_shares'), entity.cpu_shares)
equal(self._module.params.get('delete_protected'), entity.delete_protected) and and equal(self.param('delete_protected'), entity.delete_protected)
equal(self._module.params.get('use_latest_template_version'), entity.use_latest_template_version) and and equal(self.param('use_latest_template_version'), entity.use_latest_template_version)
equal(self._module.params.get('boot_devices'), [str(dev) for dev in getattr(entity.os, 'devices', [])]) and equal(self.param('boot_devices'), [str(dev) for dev in getattr(entity.os, 'devices', [])])
and equal(self.param('instance_type'), get_link_name(self._connection, entity.instance_type), ignore_case=True)
and equal(self.param('description'), entity.description)
and equal(self.param('comment'), entity.comment)
and equal(self.param('timezone'), entity.time_zone.name)
and equal(self.param('serial_policy'), str(getattr(entity.serial_number, 'policy', None)))
and equal(self.param('serial_policy_value'), getattr(entity.serial_number, 'value', None))
) )
def pre_create(self, entity): def pre_create(self, entity):
# If VM don't exists, and template is not specified, set it to Blank: # If VM don't exists, and template is not specified, set it to Blank:
if entity is None: if entity is None:
if self._module.params.get('template') is None: if self.param('template') is None:
self._module.params['template'] = 'Blank' self._module.params['template'] = 'Blank'
def post_update(self, entity): def post_update(self, entity):
@ -566,7 +622,7 @@ class VmsModule(BaseModule):
self._migrate_vm(vm_service.get()) self._migrate_vm(vm_service.get())
def _attach_cd(self, entity): def _attach_cd(self, entity):
cd_iso = self._module.params['cd_iso'] cd_iso = self.param('cd_iso')
if cd_iso is not None: if cd_iso is not None:
vm_service = self._service.service(entity.id) vm_service = self._service.service(entity.id)
current = vm_service.get().status == otypes.VmStatus.UP current = vm_service.get().status == otypes.VmStatus.UP
@ -587,7 +643,7 @@ class VmsModule(BaseModule):
return entity return entity
def _migrate_vm(self, entity): def _migrate_vm(self, entity):
vm_host = self._module.params['host'] vm_host = self.param('host')
vm_service = self._service.vm_service(entity.id) vm_service = self._service.vm_service(entity.id)
if vm_host is not None: if vm_host is not None:
# In case VM is preparing to be UP, wait to be up, to migrate it: # In case VM is preparing to be UP, wait to be up, to migrate it:
@ -606,14 +662,14 @@ class VmsModule(BaseModule):
wait( wait(
service=vm_service, service=vm_service,
condition=lambda vm: vm.status == otypes.VmStatus.UP, condition=lambda vm: vm.status == otypes.VmStatus.UP,
wait=self._module.params['wait'], wait=self.param('wait'),
timeout=self._module.params['timeout'], timeout=self.param('timeout'),
) )
def __attach_disks(self, entity): def __attach_disks(self, entity):
disks_service = self._connection.system_service().disks_service() disks_service = self._connection.system_service().disks_service()
for disk in self._module.params['disks']: for disk in self.param('disks'):
# If disk ID is not specified, find disk by name: # If disk ID is not specified, find disk by name:
disk_id = disk.get('id') disk_id = disk.get('id')
if disk_id is None: if disk_id is None:
@ -676,7 +732,7 @@ class VmsModule(BaseModule):
# Attach NICs to VM, if specified: # Attach NICs to VM, if specified:
vnic_profiles_service = self._connection.system_service().vnic_profiles_service() vnic_profiles_service = self._connection.system_service().vnic_profiles_service()
nics_service = self._service.service(entity.id).nics_service() nics_service = self._service.service(entity.id).nics_service()
for nic in self._module.params['nics']: for nic in self.param('nics'):
if search_by_name(nics_service, nic.get('name')) is None: if search_by_name(nics_service, nic.get('name')) is None:
if not self._module.check_mode: if not self._module.check_mode:
nics_service.add( nics_service.add(
@ -827,6 +883,12 @@ def main():
kernel_path=dict(default=None), kernel_path=dict(default=None),
initrd_path=dict(default=None), initrd_path=dict(default=None),
kernel_params=dict(default=None), kernel_params=dict(default=None),
instance_type=dict(default=None),
description=dict(default=None),
comment=dict(default=None),
timezone=dict(default=None),
serial_policy=dict(default=None, choices=['vm', 'host', 'custom']),
serial_policy_value=dict(default=None),
) )
module = AnsibleModule( module = AnsibleModule(
argument_spec=argument_spec, argument_spec=argument_spec,

View file

@ -51,6 +51,16 @@ options:
- "Search term which is accepted by oVirt search backend." - "Search term which is accepted by oVirt search backend."
- "For example to search VM X from cluster Y use following pattern: - "For example to search VM X from cluster Y use following pattern:
name=X and cluster=Y" name=X and cluster=Y"
all_content:
description:
- "If I(true) all the attributes of the virtual machines should be
included in the response."
case_sensitive:
description:
- "If I(true) performed search will take case into account."
max:
description:
- "The maximum number of results to return."
extends_documentation_fragment: ovirt_facts extends_documentation_fragment: ovirt_facts
''' '''
@ -78,6 +88,9 @@ ovirt_vms:
def main(): def main():
argument_spec = ovirt_facts_full_argument_spec( argument_spec = ovirt_facts_full_argument_spec(
pattern=dict(default='', required=False), pattern=dict(default='', required=False),
all_content=dict(default=False, type='bool'),
case_sensitive=dict(default=True, type='bool'),
max=dict(default=None, type='int'),
) )
module = AnsibleModule(argument_spec) module = AnsibleModule(argument_spec)
check_sdk(module) check_sdk(module)
@ -85,7 +98,12 @@ def main():
try: try:
connection = create_connection(module.params.pop('auth')) connection = create_connection(module.params.pop('auth'))
vms_service = connection.system_service().vms_service() vms_service = connection.system_service().vms_service()
vms = vms_service.list(search=module.params['pattern']) vms = vms_service.list(
search=module.params['pattern'],
all_content=module.params['all_content'],
case_sensitive=module.params['case_sensitive'],
max=module.params['max'],
)
module.exit_json( module.exit_json(
changed=False, changed=False,
ansible_facts=dict( ansible_facts=dict(