Repository: ansible-collections/community.vmware

Issue:
Feature Request: Add ability to set vm migrateencrypt attribute
<!--- Verify first that your feature was not already discussed on GitHub -->
<!--- Complete *all* sections as described, this form is processed automatically -->

##### SUMMARY
<!--- Describe the new feature/improvement briefly below -->
Add ability to set vMotion Encryption attribute. The options for this attribute are 'opportunistic', 'required', or 'disabled'.

##### ISSUE TYPE
- Feature Idea

##### COMPONENT NAME
<!--- Write the short name of the module, plugin, task or feature below, use your best guess if unsure -->
vmware_guest_custom_attributes


##### ADDITIONAL INFORMATION
<!--- Describe how the feature would be used, why it is needed and what it would solve -->

![image](https://user-images.githubusercontent.com/17625274/136038244-6a98cbf9-eea5-4c8c-a0b8-e5616b7e2952.png)


<!--- Paste example playbooks or commands between quotes below -->
```yaml

```

<!--- HINT: You can also paste gist.github.com links for larger files -->



Discussion:
I'm afraid you're misunderstanding custom attributes. [You can use custom attributes in the vSphere Client to assign user-specific values for each object of the custom attribute type.](https://docs.vmware.com/en/VMware-vSphere/7.0/com.vmware.vsphere.vcenterhost.doc/GUID-73606C4C-763C-4E27-A1DA-032E4C46219D.html)

`Encrypted vMotion` is _not_ a custom attribute. It's a configuration like whether the VM runs BIOS or UEFI. So I suggest you change the `COMPONENT NAME` to `vmware_guest`.


Resolving patch:
diff --git a/plugins/modules/vmware_guest.py b/plugins/modules/vmware_guest.py
--- a/plugins/modules/vmware_guest.py
+++ b/plugins/modules/vmware_guest.py
@@ -242,6 +242,22 @@
         iommu:
             type: bool
             description: Flag to specify if I/O MMU is enabled for this virtual machine.
+  encryption:
+    type: dict
+    default: {}
+    description:
+    - Manage virtual machine encryption settings
+    - All parameters case sensitive.
+    version_added: '3.9.0'
+    suboptions:
+        encrypted_vmotion:
+            type: str
+            description: Controlls encryption for live migrations with vmotion
+            choices: ['disabled', 'opportunistic', 'required']
+        encrypted_ft:
+            type: str
+            description: Controlls encryption for fault tolerance replication
+            choices: ['disabled', 'opportunistic', 'required']
   guest_id:
     type: str
     description:
@@ -1709,6 +1725,26 @@ def configure_hardware_params(self, vm_obj):
                     self.configspec.flags = vim.vm.FlagInfo()
                 self.configspec.flags.vbsEnabled = virt_based_security
 
+    def configure_encryption_params(self, vm_obj):
+
+        encrypted_vmotion = self.params['encryption']['encrypted_vmotion']
+        if encrypted_vmotion is not None:
+            if vm_obj is None or encrypted_vmotion != vm_obj.config.migrateEncryption:
+                self.change_detected = True
+                self.configspec.migrateEncryption = encrypted_vmotion
+
+        encrypted_ft = self.params['encryption']['encrypted_ft']
+        if encrypted_ft is not None:
+            if encrypted_ft == "disabled":
+                encrypted_ft_cfg = "ftEncryptionDisabled"
+            elif encrypted_ft == "opportunistic":
+                encrypted_ft_cfg = "ftEncryptionOpportunistic"
+            elif encrypted_ft == "required":
+                encrypted_ft_cfg = "ftEncryptionRequired"
+            if vm_obj is None or encrypted_ft_cfg != vm_obj.config.ftEncryptionMode:
+                self.change_detected = True
+                self.configspec.ftEncryptionMode = encrypted_ft_cfg
+
     def get_device_by_type(self, vm=None, type=None):
         device_list = []
         if vm is None or type is None:
@@ -2981,6 +3017,7 @@ def deploy_vm(self):
         self.configure_guestid(vm_obj=vm_obj, vm_creation=True)
         self.configure_cpu_and_memory(vm_obj=vm_obj, vm_creation=True)
         self.configure_hardware_params(vm_obj=vm_obj)
+        self.configure_encryption_params(vm_obj=vm_obj)
         self.configure_resource_alloc_info(vm_obj=vm_obj)
         self.configure_vapp_properties(vm_obj=vm_obj)
         self.configure_disks(vm_obj=vm_obj)
@@ -3165,6 +3202,7 @@ def reconfigure_vm(self):
         self.configure_guestid(vm_obj=self.current_vm_obj)
         self.configure_cpu_and_memory(vm_obj=self.current_vm_obj)
         self.configure_hardware_params(vm_obj=self.current_vm_obj)
+        self.configure_encryption_params(vm_obj=self.current_vm_obj)
         self.configure_disks(vm_obj=self.current_vm_obj)
         self.configure_network(vm_obj=self.current_vm_obj)
         self.configure_cdrom(vm_obj=self.current_vm_obj)
@@ -3449,6 +3487,13 @@ def main():
                 virt_based_security=dict(type='bool'),
                 iommu=dict(type='bool')
             )),
+        encryption=dict(
+            type='dict',
+            default={},
+            options=dict(
+                encrypted_vmotion=dict(type='str', choices=['disabled', 'opportunistic', 'required']),
+                encrypted_ft=dict(type='str', choices=['disabled', 'opportunistic', 'required'])
+            )),
         force=dict(type='bool', default=False),
         datacenter=dict(type='str', default='ha-datacenter'),
         esxi_hostname=dict(type='str'),


Test patch: