Proxmox qm CLI VM Build, Part 5: Templates, Clones, and What a Clone Actually Copies

Four posts building the same VM over and over gets old. The actual point was always this: turn the working build into a reusable base, so the next lab on this site starts from a clone instead of a fresh ISO install. This post closes the series with qm template and qm clone, and a real finding about exactly what a clone copies that’s worth knowing before relying on one.

Turning a VM into a template

Before converting VM 103, its identity was worth recording for comparison later:

$ cat /etc/machine-id
f90360b86494463f81b090c28b16866f
$ hostname
debian-cli-build
$ ssh-keygen -lf /etc/ssh/ssh_host_ed25519_key.pub
256 SHA256:rulcQX2sqlbDz/QR3uhoNysVqrBwl0PQU+GOK01yzpM root@debian-cli-build (ED25519)

qm template only works on a stopped VM:

$ sudo qm template 103
you can't convert a VM to template if VM is running
$ sudo qm stop 103
$ sudo qm template 103
  Renamed "vm-103-disk-0" to "base-103-disk-0" in volume group "pve"

Worth noticing that rename. Templating isn’t just a Proxmox-side flag, the underlying LVM volume itself gets renamed to mark it as a read-only clone source. Confirmed by trying to start it:

$ sudo qm start 103
you can't start a vm if it's a template

Clean, expected, no ambiguity.

Cloning it

$ sudo qm clone 103 105 --name dns-clone
creating a clone of VM 103 with ID 105
create linked clone of drive scsi0 (local-lvm:base-103-disk-0)
$ sudo qm start 105

Up and reachable in seconds. Compare that to Part 1’s several minutes of clicking through a netinst installer for the original. This is the actual payoff this whole series was building toward.

What a clone actually copies

The new VM’s own shell prompt gave away the first problem before any command ran: anon@debian-cli-build, the exact same hostname as the original. Checking the rest confirmed it:

$ cat /etc/machine-id
f90360b86494463f81b090c28b16866f
$ hostname
debian-cli-build
$ ssh-keygen -lf /etc/ssh/ssh_host_ed25519_key.pub
256 SHA256:rulcQX2sqlbDz/QR3uhoNysVqrBwl0PQU+GOK01yzpM root@debian-cli-build (ED25519)

Identical, all three, to the original. A clone copies the disk exactly as it was, and none of these files are excluded. Two VMs with the same /etc/machine-id, the same hostname, and the same SSH host keys, on the same network, will confuse anything that identifies hosts by those values, from DHCP leases to known_hosts entries to monitoring tools keyed off machine-id.

The commonly cited fix is rm /etc/machine-id && systemd-machine-id-setup. It didn’t work here:

$ sudo rm -f /etc/machine-id
$ sudo systemd-machine-id-setup
Initializing machine ID from D-Bus machine ID.
$ cat /etc/machine-id
f90360b86494463f81b090c28b16866f

Same value, unchanged. systemd-machine-id-setup checks /var/lib/dbus/machine-id before generating anything new, and that file was also sitting on the cloned disk with the same stale value:

$ cat /var/lib/dbus/machine-id
f90360b86494463f81b090c28b16866f

Removing both files together is the actual fix:

$ sudo rm -f /etc/machine-id /var/lib/dbus/machine-id
$ sudo systemd-machine-id-setup
Initializing machine ID from SMBIOS/DMI UUID.
$ cat /etc/machine-id
b1dc5ad1b6b145f2a6508963fb89c69f

Different this time, and it fell back to the VM’s own SMBIOS/DMI UUID once neither stale file remained. That’s a good sign in its own right: Proxmox gives every clone its own SMBIOS UUID automatically, it’s only the OS-level identity files that need clearing by hand.

SSH host keys and hostname were more straightforward:

$ sudo rm -f /etc/ssh/ssh_host_*
$ sudo dpkg-reconfigure openssh-server
$ sudo hostnamectl set-hostname dns-clone

One small trailing issue: hostnamectl doesn’t touch /etc/hosts, so its old 127.0.1.1 line kept pointing at the previous hostname, producing a harmless but noisy sudo: unable to resolve host dns-clone warning on every subsequent command until it was corrected:

$ sudo sed -i 's/debian-cli-build/dns-clone/' /etc/hosts

Where this leaves the series

Cloning VM 103 worked, but it made the actual cost of cloning a manually-installed VM concrete rather than theoretical: every identity file needs clearing by hand, and it’s easy to miss one, as the D-Bus machine-id file here proved. This is exactly the problem Part 2’s cloud-init build exists to solve. A cloud-init template regenerates hostname, network identity, and SSH host keys automatically on every boot, using the mechanism built for precisely this. For a base meant to be cloned repeatedly and unattended, the cloud-init VM from Part 2 is the better long-term template. Building it here with the ISO-installed VM instead made the mechanism, and its real cost, visible in a way a clean cloud-init clone never would have.

Five posts: a VM built from an ISO with a real boot-order bug along the way, the same VM built again with no interactive steps at all, three access methods tested against both with a genuine quirk in how two of them share one channel, a real service running on the ISO-built VM after a debugging chase that turned out to be a wrong-address mistake rather than an infrastructure problem, and a template that copies more than it looks like it should. Every command in this series ran on real hardware, including the mistakes.