feat: skip qemu-img convert — import VMDK directly via qm importdisk, only convert if per-disk shrink requested

This commit is contained in:
Claus Lohmar 2026-07-27 14:02:46 +00:00
parent 7aaa0d1553
commit 446f3ec979

View file

@ -335,19 +335,16 @@ def _process_job(job_id: str, req: JobSubmissionRequest):
except Exception: except Exception:
pass pass
# Convert with real-time progress # Import directly — qm importdisk handles conversion natively
_convert_with_progress( # Only convert if shrink was explicitly requested for this disk
job_id, source_path, output_path, disk.format, need_shrink = getattr(spec, 'target_disk_size_gb', None)
start_pct=10 + idx * 10, end_pct=55 + idx * 10, if need_shrink and need_shrink < disk.size_gb:
) _convert_with_progress(
job_id, source_path, output_path, disk.format,
# Delete source VMDK after conversion to free space start_pct=10 + idx * 10, end_pct=35 + idx * 10,
if source_path.exists() and source_path != src_path: )
try: else:
source_path.unlink() output_path = source_path # skip convert, point to original file
logger.info("Deleted source disk: %s", source_path)
except Exception:
pass
else: else:
size_gb = spec.size_gb or 32 size_gb = spec.size_gb or 32
logger.info("Creating empty disk %d: %d GiB", idx, size_gb) logger.info("Creating empty disk %d: %d GiB", idx, size_gb)
@ -358,36 +355,6 @@ def _process_job(job_id: str, req: JobSubmissionRequest):
disk_paths.append(output_path) disk_paths.append(output_path)
# ── Resize boot disk if needed ──────────────────────────────
boot_disk = disk_paths[0] if disk_paths else None
if boot_disk and boot_disk.exists():
info_json = _run(["qemu-img", "info", "--output=json", str(boot_disk)]).stdout
info = json.loads(info_json)
current_bytes = info.get("virtual-size", 0)
current_gb = current_bytes / (1024 ** 3)
target_gb = req.target_disk_size_gb
if target_gb is None:
logger.info("Disk size not specified — keeping current (%.1f GiB)", current_gb)
elif target_gb < current_gb:
_update_job(job_id, progress=60,
message=f"Shrinking disk to {target_gb} GiB...")
logger.info("Shrinking disk: %.1f GiB → %d GiB via virt-resize", current_gb, target_gb)
try:
temp = Path(str(boot_disk) + ".resized")
_run(["qemu-img", "create", "-f", "qcow2", str(temp), f"{target_gb}G"])
_run(["virt-resize", "--shrink", "--resize-force",
str(boot_disk), str(temp)], timeout=7200)
os.remove(boot_disk)
os.rename(temp, boot_disk)
logger.info("Disk shrunk successfully via virt-resize")
except Exception:
logger.warning("virt-resize failed — falling back to qemu-img resize (may corrupt FS)")
_run(["qemu-img", "resize", "--shrink", str(boot_disk), f"{target_gb}G"])
elif target_gb > current_gb:
logger.info("Expanding disk: %.1f GiB → %d GiB", current_gb, target_gb)
_run(["qemu-img", "resize", str(boot_disk), f"{target_gb}G"])
# ── Detach any existing VM with this ID ───────────────────── # ── Detach any existing VM with this ID ─────────────────────
existing = subprocess.run(["qm", "status", str(vmid)], existing = subprocess.run(["qm", "status", str(vmid)],
capture_output=True, text=True) capture_output=True, text=True)