Comprehensive validation tools for ensuring disk image integrity before migration
Hyper2KVM provides built-in validation capabilities to check disk image integrity at multiple levels before attempting migration. This helps catch corruption, format issues, and filesystem problems early in the migration process.
| Level | Speed | Requires Root | Description |
|---|---|---|---|
| Basic | Fast | No | qemu-img metadata + structure check |
| Deep | Medium | Yes | Basic + partition table inspection via NBD |
| Full | Slow | Yes | Deep + read-only filesystem checks (fsck -n) |
# Basic validation (fast, no root required)
python scripts/validate_vmdk.py /path/to/disk.vmdk
# Deep validation with partition table check
sudo python scripts/validate_vmdk.py --deep /path/to/disk.vmdk
# Full validation with filesystem integrity checks
sudo python scripts/validate_vmdk.py --full /path/to/disk.vmdk
from hyper2kvm.core.vmcraft.nbd import NBDDeviceManager
import logging
logger = logging.getLogger(__name__)
nbd = NBDDeviceManager(logger, readonly=True)
# Basic validation (fast)
metadata = nbd._validate_image('/path/to/disk.vmdk')
print(f"Format: {metadata['format']}")
print(f"Size: {metadata['virtual-size'] / (1024**3):.2f} GiB")
# Deep validation (requires sudo)
report = nbd.validate_filesystems(
'/path/to/disk.vmdk',
check_partitions=True,
run_fsck=False
)
print(f"Partitions: {len(report['partitions'])}")
# Full validation with fsck (requires sudo, slower)
report = nbd.validate_filesystems(
'/path/to/disk.vmdk',
check_partitions=True,
run_fsck=True
)
for fsck in report['fsck_results']:
print(f"{fsck['partition']}: {fsck['status']}")
# Comprehensive disk inspection with LVM (requires sudo)
report = nbd.inspect_disk(
'/path/to/disk.vmdk',
check_lvm=True,
activate_lvm=True,
run_fsck=False
)
print(f"LVM PVs: {len(report['lvm']['physical_volumes'])}")
print(f"LVM VGs: {len(report['lvm']['volume_groups'])}")
print(f"LVM LVs: {len(report['lvm']['logical_volumes'])}")
print(f"Filesystems: {len(report['filesystems'])}")
_validate_image())Fast structural validation using qemu-img
metadata = nbd._validate_image(image_path)
What it checks:
Advantages:
Returns:
Raises:
RuntimeError if image is invalid or corruptedvalidate_filesystems())Comprehensive validation with partition table inspection
report = nbd.validate_filesystems(
image_path,
format='vmdk', # Optional format hint
check_partitions=True, # Inspect partition table
run_fsck=False # Skip filesystem checks
)
What it checks:
Advantages:
Requirements:
Returns:
{
"image": "/path/to/disk.vmdk",
"format": "vmdk",
"virtual_size_gb": 100.0,
"actual_size_gb": 25.5,
"partitions": [
{"device": "nbd0p1", "info": "nbd0p1 ext4 1G ..."},
{"device": "nbd0p2", "info": "nbd0p2 swap 4G ..."}
],
"partition_table": "lsblk output...",
"fsck_results": [
{"partition": "/dev/nbd0p1", "status": "clean", "exit_code": 0},
{"partition": "/dev/nbd0p2", "status": "clean", "exit_code": 0}
],
"status": "validated"
}
Raises:
RuntimeError if validation failsFileNotFoundError if image doesn’t existinspect_disk())Complete disk structure analysis including LVM
report = nbd.inspect_disk(
image_path,
format='vmdk', # Optional format hint
check_lvm=True, # Detect LVM structures
activate_lvm=True, # Activate VGs to see LVs
run_fsck=False # Skip fsck for faster inspection
)
What it checks:
Advantages:
Requirements:
Returns:
{
"image": "/path/to/disk.vmdk",
"format": "vmdk",
"virtual_size_gb": 100.0,
"actual_size_gb": 25.5,
"partitions": [
{"device": "nbd0p1", "info": "..."}
],
"lvm": {
"physical_volumes": [
{"pv": "/dev/nbd0p2", "vg": "rhel_centos", "size": "95G"}
],
"volume_groups": [
{"vg": "rhel_centos", "pv_count": "1", "lv_count": "2", "size": "95G"}
],
"logical_volumes": [
{"lv": "root", "path": "/dev/rhel_centos/root", "size": "91G", "vg": "rhel_centos"},
{"lv": "swap", "path": "/dev/rhel_centos/swap", "size": "4G", "vg": "rhel_centos"}
]
},
"filesystems": [
{"device": "/dev/mapper/rhel_centos-root", "fstype": "xfs"},
{"device": "/dev/mapper/rhel_centos-swap", "fstype": "swap"}
],
"fsck_results": [], # Populated if run_fsck=True
"status": "inspected"
}
Use cases:
Validate images before starting migration:
from hyper2kvm.core.vmcraft.nbd import NBDDeviceManager
import logging
logger = logging.getLogger(__name__)
nbd = NBDDeviceManager(logger, readonly=True)
def validate_before_migration(image_path):
"""Validate image before migration."""
print(f"Validating: {image_path}")
# Step 1: Quick structure check
try:
metadata = nbd._validate_image(image_path)
print(f"✓ Format: {metadata['format']}")
except RuntimeError as e:
print(f"✗ Invalid image: {e}")
return False
# Step 2: Partition table check (if root)
try:
report = nbd.validate_filesystems(
image_path,
check_partitions=True,
run_fsck=False
)
print(f"✓ Partitions: {len(report['partitions'])}")
except RuntimeError as e:
print(f"⚠ Partition check failed: {e}")
print("✓ Image is ready for migration")
return True
Validate multiple images before batch migration:
#!/bin/bash
# Validate all VMDKs in a directory
for vmdk in /vms/*.vmdk; do
echo "Validating: $vmdk"
python scripts/validate_vmdk.py "$vmdk" || echo "Failed: $vmdk"
done
Integrate validation into CI/CD pipelines:
# .github/workflows/validate-images.yml
name: Validate VM Images
on: [push]
jobs:
validate:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Install dependencies
run: |
sudo apt-get update
sudo apt-get install -y qemu-utils
- name: Validate images
run: |
for img in test-images/*.vmdk; do
python scripts/validate_vmdk.py "$img"
done
scripts/validate_vmdk.pyStandalone validation script with multiple modes.
python scripts/validate_vmdk.py /path/to/disk.vmdk
Output:
======================================================================
Basic Validation: disk.vmdk
======================================================================
✓ Image Structure: VALID
Image Metadata:
Format: vmdk
Virtual Size: 100.00 GiB
Actual Size: 25.50 GiB
======================================================================
Basic validation completed successfully
======================================================================
sudo python scripts/validate_vmdk.py --deep /path/to/disk.vmdk
Output:
======================================================================
Deep Validation: disk.vmdk
======================================================================
✓ Deep Validation: PASSED
Image: /path/to/disk.vmdk
Format: vmdk
Virtual Size: 100.00 GiB
Actual Size: 25.50 GiB
Partition Table:
NAME FSTYPE SIZE LABEL UUID MOUNTPOINT
nbd0 100G
├─nbd0p1 ext4 96G root a1b2c3d4-...
└─nbd0p2 swap 4G e5f6g7h8-...
Found 2 partitions:
- nbd0p1: nbd0p1 ext4 96G root a1b2c3d4-...
- nbd0p2: nbd0p2 swap 4G e5f6g7h8-...
======================================================================
Deep validation completed successfully
======================================================================
sudo python scripts/validate_vmdk.py --full /path/to/disk.vmdk
Output:
[... deep validation output ...]
Filesystem Checks:
✓ /dev/nbd0p1: clean
✓ /dev/nbd0p2: clean
======================================================================
Full validation completed successfully
======================================================================
usage: validate_vmdk.py [-h] [--deep] [--full] [-v] [--json] image
Validate VMDK and disk images for integrity
positional arguments:
image Path to disk image (VMDK, QCOW2, VHD, etc.)
optional arguments:
-h, --help show this help message and exit
--deep Enable deep validation (partition table check via NBD)
--full Enable full validation (includes read-only fsck)
-v, --verbose Verbose output (debug logging)
--json Output results as JSON (for --deep/--full only)
examples/vmdk_validation_example.pyDemonstrates all validation methods:
# Basic validation
python examples/vmdk_validation_example.py /path/to/disk.vmdk
# Deep/full validation (requires sudo)
sudo python examples/vmdk_validation_example.py /path/to/disk.vmdk
What it demonstrates:
qemu-img check to detect corruptionqemu-img info --output=json for metadataqemu-nbd --read-onlypartprobe to scan partitionslsblk -f to inspect partition tablefsck -n (read-only) on each partitionThe validation methods handle various error conditions:
RuntimeError immediately| Validation Level | Time (typical) | Disk Access |
|---|---|---|
| Basic | 1-2 seconds | Metadata only |
| Deep | 5-10 seconds | Partition scan |
| Full | 30-300 seconds | Full read scan |
Note: Full validation time depends on disk size and filesystem complexity.
Use Basic Validation:
Use Deep Validation:
Use Full Validation:
Error: Permission denied
Solution: Deep and full validation require sudo:
sudo python scripts/validate_vmdk.py --deep disk.vmdk
Error: Failed to load NBD module
Solution: Load NBD module manually:
sudo modprobe nbd max_part=16
Error: qemu-img: command not found
Solution: Install qemu-img:
# Fedora/RHEL/CentOS
sudo dnf install qemu-img
# Ubuntu/Debian
sudo apt-get install qemu-utils
Error: invalid VMDK image descriptor
Common causes:
-flat.vmdk file instead of descriptor .vmdkSolution: Use the descriptor file (without -flat suffix)
Last Updated: January 2026 Status: Production Ready Requirements: qemu-img (basic), qemu-nbd + NBD kernel module (deep/full)