Linux VM Provisioning
Here are some steps that need to be done when creating a VM template that will be used multiple times:
Template Usage
See this page to setup a deployed instance from a template VM: Ubuntu v24 Host Setup
References
Here’s a good reference for template generation and cloud-init usage: https://medium.com/@dsykes012/making-a-custom-ubuntu-20-04-lts-focal-fossa-vm-template-that-works-with-cloud-init-2cfffb6783b4
Important Notes
Machine-ID Uniqueness: Anytime you power on a Linux VM template (whether making changes or not), you need to clear its machine-id before shutting it back down. This ensure that any generated clones will get a unique machine-id when the clone boots. If you forget to do this, the template will see that it has a machine-id, and will not generate one as a clone, causing all spawned clones to share the same machine-id.
Follow this section before powering down a template: https://wiki.galaxydump.com/link/391#bkmrk-clear-the-machine-id
Host Template Setup
Here are steps for creating a golden template VM.
Create Template VM
Create a VM guest instance with minimal CPU, memory, and hard disk space for the template.
We go with minimal resources, as it’s easier to script additional resources, than it is to reduce them.
For example, it’s much faster and less risk to expand a drive than reducing one.
Assign the VM’s NIC to the provisioning VLAN, as this allows us to easily access and setup deployed clones.
DHCP Addressing
Setup the template with DHCP, so we don’t worry about address collisions when spawning multiple clones at once.
Perform Updates and Upgrades
To speed up the process of clone setup, we will do any updates and upgrades on the template.
Do this:
apt update && apt -y upgrade && apt -y autoremove && apt clean
SSH Server
Install the openssh server.
Configure it to listen on port 22 of all adapters.
Disable password authentication over SSH.
Firewall
Setup the ufw firewall rules with 22 as allowed.
Don’t enable the firewall on the template. We can script this as use cases require.
Provisioning User Account
Create a provisioning user on the VM template.
By default, we use the username: provisioner
Sudo Bypass
Set the user account to NOT require sudo.
We do this, so that we don't have to manage passwords in the deployment scripting.
Follow this page for how to do that: Linux: Allow User to Skip Sudo Challenge
Edit the visudo file with this:
sudo visudo -f /etc/sudoers
And, add this line above the includedir line:
provisioner ALL=(ALL) NOPASSWD: ALL
Install an SSH key for the user.
Verify remote SSH access by the user.
Login as Provisioning User
Log into the template VM as root.
This allows us to scrub unnecessary users and groups from the system.
Reset Hostname
Every host needs a unique name in your network.
So, we will clear an default the hostname of a template.
The following will erase it:
truncate -s0 /etc/hostname
And, this will set it to 'localhost':
hostnamectl set-hostname localhost
Clear the Machine-Id
Machine-Id is a string value that uniquely identifies a linux host, similar to how a Windows VM is uniquely identified by its machine sid.
Linux stores the machine-id is stored in a file at: /etc/machine-id.
So. If you are cloning VMs, you need to make sure this value is different for each VM clone.
The following will erase the machine-id, and any symbolic links to it:
truncate -s0 /etc/machine-id
rm /var/lib/dbus/machine-id
ln -s /etc/machine-id /var/lib/dbus/machine-id
The next time the VM reboots, the OS will generate a new machine-id during the boot process.
NOTE: Each time you boot the template, creates a new machine Id.
So, you will need to re-execute the above, after each time you boot the template VM for updates or changes.