A Python-based tool for automating the creation of VM templates in XCP-NG using the Xen Orchestra API. This tool streamlines the process of downloading cloud images, configuring them, and converting them into ready-to-use VM templates.
This project was created to address a specific limitation in the XCP-NG ecosystem. While Packer has a provider for XCP-NG, it cannot be used to import existing disk images directly. This tool fills that gap by providing a streamlined workflow to:
- Download cloud-init compatible images from distribution repositories
- Convert them to the appropriate format
- Import them into XCP-NG storage repositories
- Create properly configured templates from these images
By automating this process, we eliminate the manual steps typically required when Packer isn't suitable for the task.
- Automated template creation from cloud images
- YAML-based configuration for easy template definition
- Concurrent template generation for efficiency
- Progress tracking with rich console output
- Support for Debian cloud images (expandable to other distributions)
- Automatic cleanup of old templates
- Python 3.8 or higher
qemu-img
installed- Access to a Xen Orchestra API endpoint
- Xen Orchestra API token
- XCP-NG server with available storage repositories
Install the required Python packages:
pip install -r requirements.txt
The tool uses a YAML configuration file to define templates. Each template consists of:
- Source configuration: Details about the cloud image to download
- Target configuration: Settings for the resulting VM template
Create a config.yml
file with the following structure:
---
templates:
debian12:
source:
distribution: debian
architecture: amd64
version: 12
variant: genericcloud
base_template: Debian Bookworm 12
target:
name: debian-12-genericcloud-amd64
cpu: 1
memory: 1
network: "Pool-wide network associated with eth1"
sr: "Local storage - srv3"
debian11:
source:
distribution: debian
architecture: amd64
version: 11
variant: genericcloud
base_template: Debian Bullseye 11
target:
name: debian-11-genericcloud-amd64
cpu: 1
memory: 1
network: "Pool-wide network associated with eth1"
sr: "Local storage - srv2"
ubuntu2404:
source:
distribution: ubuntu
architecture: amd64
version: 24.04.2
variant: live-server
base_template: Ubuntu Noble Numbat 24.04
target:
name: ubuntu-24.04.2-live-server-amd64
cpu: 1
memory: 1
network: "Pool-wide network associated with eth1"
sr: "Local storage - srv2"
Field | Description | Required | Supported Values |
---|---|---|---|
distribution |
Linux distribution | Yes | debian , ubuntu |
architecture |
CPU architecture | Yes | amd64 , arm64 |
version |
Distribution version | Yes | Integer version number (e.g., 11 , 12 ) |
variant |
Image variant | Yes | genericcloud and other Debian cloud variants |
base_template |
Name for the template in XCP-NG | Yes | Descriptive name (e.g., Debian Bookworm 12 ) |
Field | Description | Required |
---|---|---|
name |
Template name | Yes |
cpu |
Number of CPUs | Yes |
memory |
Memory in GB | Yes |
network |
XCP-NG network name to attach | Yes |
sr |
Storage repository name | Yes |
You need to provide Xen Orchestra API credentials. You can specify them in two ways:
- Environment variables:
export XOA_URL="https://your-xoa-instance.example.com"
export XOA_TOKEN="your-api-token"
- Command-line options:
python3 main.py generate --xoa-url "https://your-xoa-instance.example.com" --xoa-token "your-api-token"
# Using default config.yml file
python3 main.py generate
# Using a custom configuration file
python3 main.py generate --config my-templates.yml
# Using concurrency
python3 main.py generate --concurrency 4
./main.py list-templates
The template generation process follows these steps:
- Image Preparation: Downloads and converts the cloud image to ISO format
- Resource Collection: Gets required XCP-NG resources (storage, network, base template)
- Disk Import: Imports the disk image to XCP-NG
- VM Creation: Creates a new VM with specified parameters
- VM Configuration: Attaches the imported disk and sets boot order
- Template Conversion: Converts the VM into a template
- Cleanup: Removes older versions of the same template
The tool supports multiple verbosity levels to help with troubleshooting:
# Default level (WARNING)
python3 main.py generate
# Increased verbosity (INFO level)
python3 main.py -v generate
# Debug level (maximum verbosity)
python3 main.py -vv generate
You can use these verbosity flags with any command:
# List templates with debug output
./main.py -vv list-templates
The verbosity flag controls the detail level of log messages:
- Default: Only WARNING and above (errors and warnings)
-v
: INFO level and above (general progress information)-vv
: DEBUG level (detailed diagnostic information)
Currently, the tool supports both Debian and Ubuntu distributions. To add support for additional distributions:
- Create a new provider class that inherits from
BaseImageProvider
(service/image_providers/base.py
):
class AlpineImageProvider(BaseImageProvider):
# Code to complete
- Register your provider in the
IMAGE_PROVIDERS
dictionary:
IMAGE_PROVIDERS = {
"debian": DebianImageProvider,
"ubuntu": UbuntuImageProvider,
"alpine": AlpineImageProvider, # Add your new provider here
}
This project was inspired by the blog post Creating a Debian Cloud-Init Template in Xen Orchestra written by @mikansoro.