Skip to content
Development docs, for main @ c56b482 - what's coming, not yet released. This page for v2026.10.05-5, the latest release →

Images and formats

Every release publishes the same Janus disk in the formats private clouds import, an installer for machines without a hypervisor, and the update bundle nodes upgrade from. An image is generic: nothing in it is specific to one node - its identity is made on its first boot, its configuration given at boot or through its API afterwards (first boot).

FileForNotes
janus.qcow2Proxmox VEImported with qm importdisk, or by the Controller
janus-kvm.qcow2libvirt/KVM, any QEMU hostWhat the Controller uses on a libvirt host; virt-install --import
janus.vmdkVMware vSphere/ESXi, Workstation, FusionstreamOptimized; no OVA yet (VMware)
janus.isoBare metal; a VM installed from a mediumAn installer, with the release’s signed bundle inside: written to a USB stick, presented as a disk by a BMC, or attached to a VM as a disk - never as a CD/DVD (bare metal)
pi4-disk.img, pi5-disk.imgRaspberry Pi 4 and 5For testing only (hardware tests)
rootfs.squashfs, rootfs.squashfs.sha256, rootfs.verity, uki-a.efi, uki-b.efiUpdates and installsThe update bundle: its UKIs are signed with the release key, which pins the root filesystem’s dm-verity hash

Releases are on GitHub; latest is the newest:

Terminal window
v=$(curl -fsSL https://api.github.com/repos/swenske/Janus/releases/latest | python3 -c 'import json, sys; print(json.load(sys.stdin)["tag_name"])')
curl -fsSLO "https://github.com/swenske/Janus/releases/download/$v/janus-kvm.qcow2"

A raw disk: the qcow2 converted is the disk image the boot tests boot - qemu-img convert -O raw janus-kvm.qcow2 janus.raw - for a platform that only takes raw disks.

  • The images: GitHub computes each release file’s SHA-256 and shows it with the file; the API gives it too, and the Controller checks the images it uses against it:

    Terminal window
    curl -fsSL "https://api.github.com/repos/swenske/Janus/releases/tags/$v" \
    | python3 -c 'import json, sys; [print(a["digest"], a["name"]) for a in json.load(sys.stdin)["assets"]]'
    sha256sum janus-kvm.qcow2
  • The update bundle is checked by the node itself before it’s installed: its UKIs must be signed with the Janus release key (image/secureboot/production-cert.pem), and the root filesystem must match the dm-verity hash their signed command line carries - one changed byte and the node refuses it.

  • An image from the image factory comes with a manifest listing each file’s SHA-256.

A node’s optional features - VRRP, BGP, the firewall, Consul, Let’s Encrypt, node_exporter, the QEMU guest agent - are extensions, built into its read-only image: an image’s set of extensions is its schematic, and a node keeps its schematic through its updates. The release’s images have none; the image factory builds the others, on demand:

  • the image builder gives a schematic’s images for each platform, and its ID;
  • the Controller and Terraform ask the factory themselves: a node created with extensions = ["keepalived"] boots that image, and its updates are built from the same schematic.

Images and extensions lists the extensions and how the factory builds an image.

  • UEFI firmware - OVMF on QEMU, Proxmox’s ovmf BIOS, VMware’s EFI. No legacy BIOS boot. Secure Boot off for the VM images (their boot entries aren’t signed); every update a node installs is signed and checked anyway.
  • One disk (virtio, SCSI, SATA, NVMe): the image’s own layout - an EFI partition, two system slots for A/B updates, and STATE, a small partition keeping the node’s identity and configuration. The images are a few hundred megabytes and need no more: there’s nothing to install on a node. The installer gives STATE the rest of the disk it installs.
  • Memory and CPU: 512 MiB and one vCPU boot a test node; size a production one by its HAProxy load - two vCPUs and 2 GiB serve a lot of traffic. Without maxconn in its configuration, HAProxy sizes its tables for about 262000 connections (around 50 MB of memory): see connections and memory.
  • A serial port is worth adding: the node’s console - its first boot’s credentials, its registration’s errors - is on both the screen and the serial port, and the serial one is easier to read and copy from.
  • Network interfaces: virtio, VMware’s vmxnet3, Intel’s and Broadcom’s common ones, Mellanox ConnectX-4 and later - none needing a firmware file (physical hardware).