diff --git a/lib/ansible/modules/cloud/vmware/vmware_guest_custom_attribute_defs.py b/lib/ansible/modules/cloud/vmware/vmware_guest_custom_attribute_defs.py new file mode 100644 index 00000000000..3f1181f3450 --- /dev/null +++ b/lib/ansible/modules/cloud/vmware/vmware_guest_custom_attribute_defs.py @@ -0,0 +1,164 @@ +#!/usr/bin/python +# -*- coding: utf-8 -*- + +# Copyright: (c) 2018, Ansible Project +# +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +from __future__ import absolute_import, division, print_function +__metaclass__ = type + +ANSIBLE_METADATA = { + 'metadata_version': '1.1', + 'status': ['preview'], + 'supported_by': 'community' +} + + +DOCUMENTATION = ''' +--- +module: vmware_guest_custom_attribute_defs +short_description: Manage custom attributes definitions for virtual machine from VMWare +description: + - This module can be used to add, remove and list custom attributes definitions for the given virtual machine from VMWare. +version_added: 2.7 +author: + - Jimmy Conner + - Abhijeet Kasurde (@Akasurde) +notes: + - Tested on vSphere 6.5 +requirements: + - "python >= 2.6" + - PyVmomi +options: + attribute_key: + description: + - Name of the custom attribute definition. + - This is required parameter, if C(state) is set to C(present) or C(absent). + required: False + state: + description: + - Manage definition of custom attributes. + - If set to C(present) and definition not present, then custom attribute definition is created. + - If set to C(present) and definition is present, then no action taken. + - If set to C(absent) and definition is present, then custom attribute definition is removed. + - If set to C(absent) and definition is absent, then no action taken. + default: 'present' + choices: ['present', 'absent'] + required: True +extends_documentation_fragment: vmware.documentation +''' + +EXAMPLES = ''' +- name: List VMWare Attribute Definitions + vmware_guest_custom_attribute_defs: + hostname: 192.168.1.209 + username: administrator@vsphere.local + password: vmware + validate_certs: no + state: list + delegate_to: localhost + register: defs + +- name: Add VMWare Attribute Definition + vmware_guest_custom_attribute_defs: + hostname: 192.168.1.209 + username: administrator@vsphere.local + password: vmware + validate_certs: no + state: present + attribute_key: custom_attr_def_1 + delegate_to: localhost + register: defs + +- name: Remove VMWare Attribute Definition + vmware_guest_custom_attribute_defs: + hostname: 192.168.1.209 + username: administrator@vsphere.local + password: vmware + validate_certs: no + state: absent + attribute_key: custom_attr_def_1 + delegate_to: localhost + register: defs +''' + +RETURN = """ +custom_attribute_defs: + description: list of all current attribute definitions + returned: always + type: list + sample: ["sample_5", "sample_4"] +""" + +from ansible.module_utils.basic import AnsibleModule +from ansible.module_utils.vmware import PyVmomi, vmware_argument_spec + +try: + import pyVmomi + from pyVmomi import vim +except ImportError: + pass + + +class VmAttributeDefManager(PyVmomi): + def __init__(self, module): + super(VmAttributeDefManager, self).__init__(module) + self.custom_field_mgr = self.content.customFieldsManager.field + + def remove_custom_def(self, field): + changed = False + f = dict() + for x in self.custom_field_mgr: + if x.name == field: + changed = True + if not self.module.check_mode: + self.content.customFieldsManager.RemoveCustomFieldDef(key=x.key) + break + f[x.name] = (x.key, x.managedObjectType) + return {'changed': changed, 'failed': False, 'custom_attribute_defs': list(f.keys())} + + def add_custom_def(self, field): + changed = False + found = False + f = dict() + for x in self.custom_field_mgr: + if x.name == field: + found = True + f[x.name] = (x.key, x.managedObjectType) + + if not found: + changed = True + if not self.module.check_mode: + new_field = self.content.customFieldsManager.AddFieldDefinition(name=field, moType=vim.VirtualMachine) + f[new_field.name] = (new_field.key, new_field.type) + return {'changed': changed, 'failed': False, 'custom_attribute_defs': list(f.keys())} + + +def main(): + argument_spec = vmware_argument_spec() + argument_spec.update( + attribute_key=dict(type='str'), + state=dict(type='str', default='present', choices=['absent', 'present']), + ) + module = AnsibleModule( + argument_spec=argument_spec, + supports_check_mode=True, + required_if=[ + ['state', 'present', ['attribute_key']], + ['state', 'absent', ['attribute_key']], + ] + ) + + pyv = VmAttributeDefManager(module) + results = dict(changed=False, custom_attribute_defs=list()) + if module.params['state'] == "present": + results = pyv.add_custom_def(module.params['attribute_key']) + elif module.params['state'] == "absent": + results = pyv.remove_custom_def(module.params['attribute_key']) + + module.exit_json(**results) + + +if __name__ == '__main__': + main() diff --git a/test/integration/targets/vmware_guest_custom_attribute_defs/aliases b/test/integration/targets/vmware_guest_custom_attribute_defs/aliases new file mode 100644 index 00000000000..845e8a6dad5 --- /dev/null +++ b/test/integration/targets/vmware_guest_custom_attribute_defs/aliases @@ -0,0 +1,2 @@ +cloud/vcenter +unsupported diff --git a/test/integration/targets/vmware_guest_custom_attribute_defs/tasks/main.yml b/test/integration/targets/vmware_guest_custom_attribute_defs/tasks/main.yml new file mode 100644 index 00000000000..06674f279b3 --- /dev/null +++ b/test/integration/targets/vmware_guest_custom_attribute_defs/tasks/main.yml @@ -0,0 +1,157 @@ +# Test code for the vmware_guest_custom_attribute_defs module. +# Copyright: (c) 2018, Abhijeet Kasurde +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +- name: store the vcenter container ip + set_fact: + vcsim: "{{ lookup('env', 'vcenter_host') }}" + +- debug: var=vcsim + +- name: Wait for Flask controller to come up online + wait_for: + host: "{{ vcsim }}" + port: 5000 + state: started + +- name: kill vcsim + uri: + url: http://{{ vcsim }}:5000/killall + +- name: start vcsim + uri: + url: http://{{ vcsim }}:5000/spawn?datacenter=1&cluster=1&folder=0 + register: vcsim_instance + +- name: Wait for vcsim server to come up online + wait_for: + host: "{{ vcsim }}" + port: 443 + state: started + +- name: list custom attributes + vmware_guest_custom_attribute_defs: + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + validate_certs: False + state: list + register: list_attrib_def + +- debug: var=list_attrib_def + +- assert: + that: + - "not list_attrib_def.changed" + +- name: add custom attribute definition + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: present + attribute_key: sample_5 + register: add_attrib_def + +- debug: var=add_attrib_def + +- assert: + that: + - "add_attrib_def.changed" + - "'sample_5' in add_attrib_def.instance" + +- name: list custom attributes + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: list + register: list_attrib_def + +- debug: var=list_attrib_def + +- assert: + that: + - "not list_attrib_def.changed" + +- name: add attribute definition again + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: present + attribute_key: sample_5 + register: add_attrib_def + +- debug: var=add_attrib_def + +- assert: + that: + - "not add_attrib_def.changed" + +- name: list attribute definition + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: list + register: list_attrib_def + +- debug: var=list_attrib_def + +- assert: + that: + - "not list_attrib_def.changed" + +- name: remove attribute definition + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: absent + attribute_key: sample_5 + register: remove_attrib_def + +- debug: var=remove_attrib_def + +- assert: + that: + - "remove_attrib_def.changed" + - "'sample_5' not in remove_attrib_def.instance" + +- name: remove attribute definition + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: absent + attribute_key: sample_5 + register: remove_attrib_def + +- debug: var=remove_attrib_def + +- assert: + that: + - "not remove_attrib_def.changed" + - "'sample_5' not in remove_attrib_def.instance" + +- name: list attribute definition + vmware_guest_custom_attribute_defs: + validate_certs: False + hostname: "{{ vcsim }}" + username: "{{ vcsim_instance['json']['username'] }}" + password: "{{ vcsim_instance['json']['password'] }}" + state: list + register: list_attrib_def + +- debug: var=list_attrib_def + +- assert: + that: + - "not list_attrib_def.changed"