Skip to main content
RunBook Academy

Proxmox VEIX · Virtual MachinesProvisioning

Cloud-Init, templates, and clones

Intermediate⏱ ~16 min

What you'll learn

  • Configure a VM as a Cloud-Init template
  • Generate linked clones vs full clones based on use case
  • Customise instances at first boot via Cloud-Init
  • Manage the template lifecycle

Prerequisites

Verified against Proxmox VE 9.2.4 · Proxmox Backup Server 4.2.5 · Ceph Squid / Tentacle · Debian 13 (Trixie) · Linux kernel 7.0 (PVE 9.2 default) · 2026-08-07

Not yet marked complete on this device.

Why this matters in production

Manually installing 30 VMs is not feasible. Cloud-Init + templates lets you provision VMs consistently at scale.

The pattern

flowchart LR
  A[Install base OS in VM] --> B[Customise: packages, config]
  B --> C[Install cloud-init guest]
  C --> D[Clean up & convert to template]
  D --> E[Template]
  E --> F[Clone for each instance]
  F --> G[Customise on first boot]

Step 1: Create a base VM

Install a base OS in a VM exactly as you would for a single instance. Apply your standard configuration: packages, users, security settings.

Step 2: Install the Cloud-Init guest

In the base VM:

apt update && apt install -y cloud-init qemu-guest-agent
dnf install -y cloud-init qemu-guest-agent

For Windows, install cloudbase-init.

Step 3: Clean up

Before converting to a template, remove machine-specific data:

cloud-init clean --logs --seed
rm -f /etc/ssh/ssh_host_*
rm -f /var/lib/dhcp/*
history -c && shutdown -h now

Step 4: Convert to a template

In the GUI: right-click the VM → “Convert to Template”. CLI:

qm template 9000

Step 5: Clone instances

GUI: right-click the template → Clone. CLI:

qm clone 9000 100 --name web-01 --full 1
qm clone 9000 101 --name web-02 --full 0
Clone typeStorageSpeedUse
FullIndependent copySlow (copies data)Production VMs that may diverge significantly
LinkedSnapshot-based deltaFast (instant)Disposable, dev, fast scaling

Step 6: Customise on first boot

Proxmox passes Cloud-Init configuration to the VM at boot:

qm set 101 --ciuser admin --cipassword <hash> --sshkeys /root/.ssh/id_rsa.pub --ipconfig0 ip=10.10.100.50/24,gw=10.10.100.1 --searchdomain lab.example.com --nameserver 10.10.10.1
qm cloudinit update 101 && qm start 101

Common Cloud-Init parameters:

ParameterPurpose
ciuserDefault user to create
cipassword(Hashed) password
sshkeysSSH public keys
ipconfig0Static IP / gateway
searchdomainDNS search domain
nameserverDNS server
cicustomCustom Cloud-Init script (meta, user, vendor)

Production considerations

Common mistakes

  • Storing plaintext passwords in Cloud-Init configuration.
  • Modifying a template after conversion (it’s locked).
  • Deleting the base disk of a template with linked clones.
  • Forgetting to install cloud-init in the base VM.

Key takeaways

  • Templates + Cloud-Init is the production way to provision at scale.
  • Use mkpasswd --method=SHA-512 for password hashes.
  • Linked clones share storage with the template; full clones are independent.

Knowledge check

Knowledge check · 3 questions

  1. Q1. Which command converts a VM to a template?

  2. Q2. A linked clone keeps reading from the template base disk, so the template cannot be removed while clones of it exist.

  3. Q3. Which command generates a password hash suitable for cipassword?

Passing score: 75%. Answers are checked in this browser.