#!/bin/bash set -Eeuo pipefail if [[ $# -ne 1 ]]; then echo "Usage: $0 " exit 1 fi VM="${1}" if [ -d "/var/lib/libvirt/images/${VM}/" ]; then echo "VM ${VM} already exists. Please remove it first." exit 1 fi temp_dir=$(mktemp -d) cleanup() { local exit_code=$? rm -rf "$temp_dir" if [ $exit_code -ne 0 ]; then echo "An error occurred. Cleaning up..." virsh destroy "${VM}" || true virsh undefine "${VM}" --nvram || true rm -rf "/var/lib/libvirt/images/${VM}/" fi } trap cleanup EXIT # This function extracts the first layer blob from a Podman artifact and saves it to the specified output file. # It is used when the "podman artifact extract" command is not available. function podman_artifact_extract() { local ARTIFACT="$1" local OUTPUT_FILE="$2" local container_id local DIGEST_WITH_ALGO="$(podman artifact inspect $ARTIFACT | jq -r '.Manifest.layers[0].digest')" local FILENAME="$(podman artifact inspect $ARTIFACT | jq -r '.Manifest.layers[0].annotations["org.opencontainers.image.title"]')" echo "Extracting blob $DIGEST_WITH_ALGO ($FILENAME) from artifact $ARTIFACT to $OUTPUT_FILE..." local BLOB_HASH="${DIGEST_WITH_ALGO#sha256:}" local SOURCE_PATH="$(find /var/lib/containers/storage -type f -name $BLOB_HASH)" if [ -z "$SOURCE_PATH" ]; then echo "Blob $BLOB_HASH not found in container storage!" return 1 fi cp "$SOURCE_PATH" "$OUTPUT_FILE" } # Create a temporary directory to hold the VM image and copy the base image there install -m 0710 -o root -g qemu --context=system_u:object_r:virt_image_t:s0 -d "$temp_dir" # Pull the base image defined in the environment file podman artifact pull "${DOMAIN_DISK_SOURCE}" #podman artifact extract "${DOMAIN_DISK_SOURCE}" "$temp_dir/root.qcow2" podman_artifact_extract "${DOMAIN_DISK_SOURCE}" "$temp_dir/root.qcow2" chown root:qemu "$temp_dir/root.qcow2" chmod 0660 "$temp_dir/root.qcow2" chcon system_u:object_r:virt_image_t:s0 "$temp_dir/root.qcow2" # Inject the Flightctl configuration file (w/ enrollment certificates) into the VM image # Note: The injected config file will be moved to the right place in the VM by a systemd override in the base image if [ -f /etc/flightctl/config.yaml ]; then if [ -n "${FLIGHTCTL_LABELS_OVERRIDE:-}" ]; then echo "Overriding default labels with: ${FLIGHTCTL_LABELS_OVERRIDE}" yq e ". * { \"default-labels\": ${FLIGHTCTL_LABELS_OVERRIDE} } | .default-labels.aap_group = ((.default-labels.site + \"_\" + .default-labels.type) | sub(\"-\", \"_\"))" /etc/flightctl/config.yaml > "$temp_dir/config.yaml" else cp /etc/flightctl/config.yaml "$temp_dir/config.yaml" fi echo "Injecting Flightctl configuration into the VM image..." guestfish --add "$temp_dir/root.qcow2" -m /dev/sda4 <