Using virt-builder & virsh to create, customize, and manage VMs

Here's the workflow that I use for creating/managing KVM- and QEMU-based VMs:

Prerequisites

Make sure you have satisfied the following:

Build, import and manage the VM

  1. Build a VM image.

    virt-builder lets you rapidly create and customize virtual machine disk iamges.  When you first run virt-builder to create, say, an Ubuntu VM, it'll create the disk image (and then caches a a compressed template - the location is ~/.cache/virt-builder/). So the first run will take a few minutes; after that every new VM image creation will take just about a minute or so.

    Example usage:

    • Find what OS disk images virt-builder supports:

      $ virt-builder --list | less
    • Simple usage: build an Ubuntu "Focal" disk image image, of QCOW2 format, 20G size, with a root password of your choice:

      $ cd /var/lib/libvirt/images/
      
      $ sudo virt-builder ubuntu-20.04 --format qcow2 --size 20G \
          -o focal-vm1.qcow2 --root-password secret
  2. Import the image to libvirt.

    Once you have the disk image, ubuntu-focal-vm.qcow2, you want to import it into libvirt so that you can manage it with libvirt's shell tool, virsh.

    Assuming you have libvirtd running you can import the disk image you created in step (1) with the virt-install command (note: we're not installing anything here, but merely importing the disk image into libvirt). The VM gets 4GM (4096 MB), so make sure that's available:

    $ sudo virt-install --name focal-vm1 --ram 4096 \
        --disk path=/var/lib/libvirt/images/focal-vm1.qcow2,format=qcow2 \
        --nographics --os-variant ubuntu20.04 --import

Managing VMs with virsh

A quick usage of virsh (you can also the GUI tool virt-manager, or GNOME Boxes).

To list all the virtual machines (online and offline):

$ sudo virsh list --all

Start a VM, and see the boot process on the serial console

$ sudo virsh start --console

To take an "internal" snapshot of your VM:

$ sudo virsh snapshot-create-as focal-vm1 snap1 "Clean Focal 1"

With this kind of snapshot (called "internal snapshots"), the original and its delta, i.e. the snapshot, are stored in a single disk image file; this is convenient for moving it across machines. This only works with QCOW2 images.

To revert to the snapshot:

$ sudo virsh snapshot-revert focal-vm1 snap1

To gracefully shutdown and delete a VM, including its disk image:

$ sudo virsh stop f27vm1
$ sudo virsh undefine f27vm1 --remove-all-storage

Docs