In my current job we use Proxmox clusters as VM hosts and a lot of Debian VM on them. Most of the VMs are old and handcrafted but for some of them like Jenkins agents and Gitlab runners I created Ansible playbooks to configure them. Of course this is rather useless if there is no way to automatically spawn the whole VM before configuring it and so I started to create a role which creates the VM if it’s not already existing.

The basic concept is simple. On every physical host there is a template VM which contains a untouched Debian Cloud image. If the VM doesn’t exist, this template is cloned and the VM parameters are set via the Proxmox API. The initial config which is necessary for Ansible to ssh into the VM later are passed via cloud-init.

The role follows the same basic concept of my systemd-nspawn container role, all the parameters of the created machines shall be defined in a host_vars/name.yml looking like this:

physical_host: kvm-server-99
vm_cores: 32
vm_memory: 32768
vm_disksize: "20G"
vm_template: "debian11-cloudinit-template"

With that set it is enough to call the role as first task of the playbook and the VM will be spawned.

Over time the role became more complex so I decided to release it on Github to share it with the community.