From a9403fd090002898b51ba9b466afe5aa22e9fd50 Mon Sep 17 00:00:00 2001 From: Ronald Date: Wed, 19 Jun 2024 21:46:06 +0100 Subject: [PATCH] Initial commit --- README.md | 27 +++++++++++ defaults/main.yml | 19 ++++++++ meta/main.yml | 8 ++++ tasks/connect.yml | 36 ++++++++++++++ tasks/main.yml | 34 +++++++++++++ tasks/proxmox.yml | 119 ++++++++++++++++++++++++++++++++++++++++++++++ vars/main.yml | 21 ++++++++ 7 files changed, 264 insertions(+) create mode 100644 README.md create mode 100644 defaults/main.yml create mode 100644 meta/main.yml create mode 100644 tasks/connect.yml create mode 100644 tasks/main.yml create mode 100644 tasks/proxmox.yml create mode 100644 vars/main.yml diff --git a/README.md b/README.md new file mode 100644 index 0000000..75561cb --- /dev/null +++ b/README.md @@ -0,0 +1,27 @@ +# Role Name: create_vm_proxmox + +A simple role to create/clone virtual machines in Proxmox. + +## Role variables + +TODO: Add table of role variables + +## Dependencies + +Python module on the host used in proxmox tasks +- `requests` +- `proxmoxer` + +Bash is required for the connect tasks + +## Example Playbook + +Example playbook: + + - hosts: virtual_servers + roles: + - create_vm_proxmox + +## License + +BSD-3-Clause License diff --git a/defaults/main.yml b/defaults/main.yml new file mode 100644 index 0000000..2ecc0e0 --- /dev/null +++ b/defaults/main.yml @@ -0,0 +1,19 @@ +--- +# defaults file for Create-VM +# Generic Variables # +create_vm_proxmox_recreate_vm: false + +# promxox specific default variables # +create_vm_proxmox_start_vm: true +create_vm_proxmox_configure_cloudinit: true +create_vm_proxmox_enable_guest_agent: true +create_vm_proxmox_start_vm_onboot: true + +# cloud-init variables # +create_vm_proxmox_cloudinit_storage_pool: local-lvm + +# connection variables # +create_vm_proxmox_connect_to_vm: true +create_vm_proxmox_remove_ssh_host_key: true + +... diff --git a/meta/main.yml b/meta/main.yml new file mode 100644 index 0000000..cc8822a --- /dev/null +++ b/meta/main.yml @@ -0,0 +1,8 @@ +galaxy_info: + role_name: create_vm_proxmox + author: Ronald + description: Creates virtual machines in Proxmox from templates + + license: BSD-3-Clause + + min_ansible_version: "2.17" diff --git a/tasks/connect.yml b/tasks/connect.yml new file mode 100644 index 0000000..8d5babd --- /dev/null +++ b/tasks/connect.yml @@ -0,0 +1,36 @@ +--- + +- name: Ensure we don't have an incorrect SSH host key stored on the Ansible controller + ansible.builtin.command: + cmd: "ssh-keygen -R {{ ansible_host }}" + register: create_vm_proxmox_remove_ssh_host_key_cmd + changed_when: + - '"# Host " + ansible_host + " found" in create_vm_proxmox_remove_ssh_host_key_cmd.stdout' + when: + - create_vm_proxmox_remove_ssh_host_key | bool + delegate_to: localhost + +- name: Wait for SSH to become available + ansible.builtin.wait_for: + host: "{{ ansible_host }}" + port: 22 + delay: 10 + timeout: 120 + delegate_to: localhost + +- name: Get SSH host key + ansible.builtin.shell: + cmd: "ssh-keyscan {{ ansible_host }} >> ~/.ssh/known_hosts" + args: + executable: /bin/bash + changed_when: true + delegate_to: localhost + +- name: Ensure we can connect + ansible.builtin.wait_for_connection: + connect_timeout: 10 + delay: 5 + sleep: 2 + timeout: 120 + +... diff --git a/tasks/main.yml b/tasks/main.yml new file mode 100644 index 0000000..6e198b0 --- /dev/null +++ b/tasks/main.yml @@ -0,0 +1,34 @@ +--- +# tasks file for Create-VM + +- name: Check that all required variables are declared + ansible.builtin.fail: + msg: "{{ item }} is undefined" + when: + - vars[item] is undefined + loop: "{{ create_vm_proxmox_required_vars }}" + +- name: Check that required variables for proxmox are defined + ansible.builtin.fail: + msg: "{{ item }} is undefined" + loop: "{{ create_vm_proxmox_required_vars }}" + when: + - vars[item] is undefined + +- name: Check that required variables for Proxmox cloud-init are defined + ansible.builtin.fail: + msg: "{{ item }} is undefined" + loop: "{{ create_vm_proxmox_required_vars_cloudinit }}" + when: + - vars[item] is undefined + +- name: Include Proxmox tasks + ansible.builtin.include_tasks: proxmox.yml + +- name: Include tasks to connect to the new VM + ansible.builtin.include_tasks: + file: connect.yml + when: + - create_vm_proxmox_connect_to_vm | bool + +... diff --git a/tasks/proxmox.yml b/tasks/proxmox.yml new file mode 100644 index 0000000..9a30c02 --- /dev/null +++ b/tasks/proxmox.yml @@ -0,0 +1,119 @@ +--- + +- name: Check if VM already exists + community.general.proxmox_vm_info: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + vmid: "{{ create_vm_proxmox_vmid }}" + register: create_vm_proxmox_check_if_vm_exists + when: + - create_vm_proxmox_recreate_vm | bool + delegate_to: localhost + +- name: Delete VM if it already exists + community.general.proxmox_kvm: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + vmid: "{{ create_vm_proxmox_vmid }}" + name: "{{ create_vm_proxmox_name }}" + state: absent + force: true + when: + - create_vm_proxmox_check_if_vm_exists.proxmox_vms is defined + - create_vm_proxmox_check_if_vm_exists.proxmox_vms | length > 0 + - create_vm_proxmox_recreate_vm | bool + delegate_to: localhost + +- name: Check if VM already exists + community.general.proxmox_vm_info: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + vmid: "{{ create_vm_proxmox_vmid }}" + register: create_vm_proxmox_check_if_vm_exists + delegate_to: localhost + +- name: Clone VM in Proxmox + community.general.proxmox_kvm: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + node: "{{ create_vm_proxmox_host }}" + newid: "{{ create_vm_proxmox_vmid }}" + name: "{{ create_vm_proxmox_name }}" + clone: "{{ create_vm_proxmox_source_vm }}" + vcpus: "{{ create_vm_proxmox_numb_cpus | default(omit) }}" + cores: "{{ create_vm_proxmox_numb_cores | default(omit) }}" + memory: "{{ create_vm_proxmox_memory_mb | default(omit) }}" + virtio: "{{ create_vm_proxmox_virtio_disks | default(omit) }}" + net: "{{ create_vm_proxmox_net | default(omit) }}" + when: + - create_vm_proxmox_check_if_vm_exists.proxmox_vms | length == 0 + delegate_to: localhost + +- name: Add cloud-init drive to VM + community.general.proxmox_kvm: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + node: "{{ create_vm_proxmox_host }}" + vmid: "{{ create_vm_proxmox_vmid }}" + name: "{{ create_vm_proxmox_name }}" + update: true + update_unsafe: true + ciuser: "{{ create_vm_proxmox_cloudinit_user }}" + cipassword: "{{ create_vm_proxmox_cloudinit_user }}" + sshkeys: "{{ create_vm_proxmox_cloudinit_sshkeys }}" + ipconfig: "{{ create_vm_proxmox_cloudinit_ipconfig }}" + nameservers: "{{ create_vm_proxmox_cloudinit_nameservers }}" + searchdomains: "{{ create_vm_proxmox_cloudinit_searchdomains }}" + ide: + ide2: "{{ create_vm_proxmox_cloudinit_storage_pool }}:cloudinit,format=raw" + when: + - create_vm_proxmox_check_if_vm_exists.proxmox_vms | length == 0 + - create_vm_proxmox_configure_cloudinit | bool + delegate_to: localhost + +- name: Start VM + community.general.proxmox_kvm: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + node: "{{ create_vm_proxmox_host }}" + vmid: "{{ create_vm_proxmox_vmid }}" + name: "{{ create_vm_proxmox_name }}" + state: started + when: + - create_vm_proxmox_start_vm + delegate_to: localhost + +- name: Enable QEMU guest agent for VM + community.general.proxmox_kvm: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + node: "{{ create_vm_proxmox_host }}" + vmid: "{{ create_vm_proxmox_vmid }}" + name: "{{ create_vm_proxmox_name }}" + agent: true + when: + - create_vm_proxmox_enable_guest_agent | bool + delegate_to: localhost + +- name: Set VM to autostart + community.general.proxmox_kvm: + api_host: "{{ create_vm_proxmox_host }}" + api_user: "{{ create_vm_proxmox_user }}" + api_password: "{{ create_vm_proxmox_password }}" + node: "{{ create_vm_proxmox_host }}" + vmid: "{{ create_vm_proxmox_vmid }}" + name: "{{ create_vm_proxmox_name }}" + proxmox_default_behavior: no_defaults + onboot: true + when: + - create_vm_proxmox_start_vm_onboot | bool + delegate_to: localhost + +... diff --git a/vars/main.yml b/vars/main.yml new file mode 100644 index 0000000..01dafb0 --- /dev/null +++ b/vars/main.yml @@ -0,0 +1,21 @@ +--- +# vars file for Create-VM + +create_vm_proxmox_required_vars: + - create_vm_proxmox_host + - create_vm_proxmox_name + - create_vm_proxmox_user + - create_vm_proxmox_password + - create_vm_proxmox_vmid + - create_vm_proxmox_source_vm + +create_vm_proxmox_required_vars_cloudinit: + - create_vm_proxmox_cloudinit_storage_pool + - create_vm_proxmox_cloudinit_user + - create_vm_proxmox_cloudinit_password + - create_vm_proxmox_cloudinit_sshkeys + - create_vm_proxmox_cloudinit_ipconfig + - create_vm_proxmox_cloudinit_nameservers + - create_vm_proxmox_cloudinit_searchdomains + +...