New extension: nvme-conversion — Convert VM disk controllers between SCSI and NVMe#9858
New extension: nvme-conversion — Convert VM disk controllers between SCSI and NVMe#9858jonathanbrenes wants to merge 3 commits into
Conversation
…SCSI and NVMe Adds the nvme-conversion extension that orchestrates the full SCSI<->NVMe conversion lifecycle for Azure VMs: - Pre-flight validation (Gen2, ADE, SKU capabilities, OS readiness) - OS preparation via RunCommand (Windows stornvme, Linux initramfs/grub/fstab) - VM deallocate, OS disk capability update, VM resize + controller change - Optional VM start with rollback instructions Commands: az nvme-conversion check - Validate VM readiness without changes az nvme-conversion convert - Full conversion with --fix-os, --dry-run, --no-wait Tested on: Ubuntu 24.04, RHEL 8/9/10, SLES 15 SP6, Azure Linux 4, Windows Server 2019/2022 — 20 VMs, 56 unit tests, azdev style/test/linter passed.
- custom.py: reject unmanaged (page-blob) OS disks in _validate_vm with a clear ValidationError. - custom.py: add _get_vm_skus() helper; share resource_skus.list() result between _resolve_vm_size and _validate_sku to avoid duplicate API calls. - custom.py: switch user-progress logger.warning calls to logger.info (Gen2 banner, controller arrows, SKU validating, VM updated, VM started, etc.); reserve warnings for actual problems. - custom.py: collapse _check_os_readiness into a thin wrapper around _prepare_os(fix_os=False, dry_run=False) to remove duplicated logic. - custom.py: validate SKU capabilities across all vm.zones, not just vm.zones[0]. - _linux_checks.py / _windows_checks.py: add timeout=600 to begin_run_command(...).result() calls so RunCommand cannot hang indefinitely. - commands.py: replace confirmation=True with a custom yes/no prompt that names the VM and target controller for the convert command. - setup.py: pin azure-mgmt-compute>=30.0.0. Validated end-to-end against live Azure VMs in westus3: - 6/6 RHEL 9 LVM Gen2 VMs converted Standard_D2s_v5 (SCSI) -> Standard_D2s_v6 (NVMe) and verified post-conversion. - Unmanaged-disk guard verified live: az nvme-conversion check on an unmanaged-disk VM fails with the new clear error message. - pytest: 56 passed, 2 skipped. azdev style (pylint + flake8): PASSED.
|
Validation for Breaking Change Starting...
Thanks for your contribution! |
There was a problem hiding this comment.
Pull request overview
Note
Copilot was unable to run its full agentic suite in this review.
Adds a new Azure CLI extension (nvme-conversion) to pre-flight check and convert Azure VM disk controllers between SCSI and NVMe, including OS readiness checks/fixes and user-facing help/output.
Changes:
- Introduces
az nvme-conversion checkandaz nvme-conversion convertcommands with SKU/ADE/Gen2/power-state validation and conversion orchestration. - Adds OS preparation implementations for Linux (embedded RunCommand bash script) and Windows (stornvme checks/fix via RunCommand).
- Adds unit + mocked end-to-end tests plus extension packaging metadata and docs.
Reviewed changes
Copilot reviewed 22 out of 22 changed files in this pull request and generated 12 comments.
Show a summary per file
| File | Description |
|---|---|
| src/nvme-conversion/setup.py | Extension packaging metadata and dependencies |
| src/nvme-conversion/setup.cfg | Placeholder config file |
| src/nvme-conversion/azext_nvme_conversion/custom.py | Primary check/convert orchestration and internal helpers |
| src/nvme-conversion/azext_nvme_conversion/commands.py | CLI command registration + confirmation/table formatting wiring |
| src/nvme-conversion/azext_nvme_conversion/_params.py | CLI parameters and validators wiring |
| src/nvme-conversion/azext_nvme_conversion/_validators.py | Input validation for --vm-size and --sleep-seconds |
| src/nvme-conversion/azext_nvme_conversion/_windows_checks.py | Windows RunCommand checks/fix + version validation |
| src/nvme-conversion/azext_nvme_conversion/_linux_checks.py | Linux RunCommand wrapper and error parsing |
| src/nvme-conversion/azext_nvme_conversion/_linux_script.py | Embedded bash script for Linux NVMe readiness + fixes |
| src/nvme-conversion/azext_nvme_conversion/_format.py | Table output transformers for -o table |
| src/nvme-conversion/azext_nvme_conversion/_help.py | Help text and examples |
| src/nvme-conversion/azext_nvme_conversion/_client_factory.py | Compute client factory |
| src/nvme-conversion/azext_nvme_conversion/azext_metadata.json | Extension metadata (preview + min CLI core) |
| src/nvme-conversion/azext_nvme_conversion/tests/latest/test_nvme_conversion.py | Unit + mocked end-to-end tests |
| src/nvme-conversion/README.md | User-facing overview and usage |
| src/nvme-conversion/HISTORY.rst | Initial release notes |
| src/nvme-conversion/DEVELOPMENT.md | Development guide and architecture notes |
| src/nvme-conversion/ROADMAP.md | Implementation roadmap and design notes |
| src/nvme-conversion/TESTING.md | Live test tracker |
| # Resolve VM size: use current if not specified and current supports the target controller | ||
| _status('[2/8] Resolving VM size...') | ||
| vm_size = _resolve_vm_size(compute_client, vm, vm_size, new_controller_type, | ||
| ignore_sku_check, vm_skus=vm_skus) |
There was a problem hiding this comment.
Fixed in b9e5df3. Updated HISTORY.rst and PR description to accurately describe behavior: auto-detects controller type; reuses current VM size if compatible, otherwise requires --vm-size.
| # Windows version | ||
| if os_type == 'Windows' and not ignore_windows_version_check: | ||
| _status('[5/7] Checking Windows version...') |
There was a problem hiding this comment.
Fixed in b9e5df3. Renumbered to [5/7] for Windows version check and [6/7] for SKU validation.
|
Thank you for your contribution! We will review the pull request and get back to you soon. |
|
The git hooks are available for azure-cli and azure-cli-extensions repos. They could help you run required checks before creating the PR. Please sync the latest code with latest dev branch (for azure-cli) or main branch (for azure-cli-extensions). pip install azdev --upgrade
azdev setup -c <your azure-cli repo path> -r <your azure-cli-extensions repo path>
|
|
New extension:
nvme-conversion— Convert VM disk controllers between SCSI and NVMeRelated command
az nvme-conversion check,az nvme-conversion convertDescription
Adds a new Azure CLI extension that converts Azure VM disk controllers between SCSI and NVMe. This is a preview release (
1.0.0b1).Key capabilities:
az nvme-conversion check— Pre-flight validation (SKU capabilities, OS readiness, VM generation, ADE, unmanaged-disk detection) without making changesaz nvme-conversion convert— End-to-end conversion: validates prerequisites, prepares the OS, resizes the VM to an NVMe-capable SKU, and restarts--dry-run)Standard_D2s_v5→Standard_D2s_v6)Testing:
azdev style nvme-conversion(pylint + flake8): PASSEDStandard_D2s_v5(SCSI) →Standard_D2s_v6(NVMe) and verified post-conversionGeneral Guidelines
azdev style <YOUR_EXT>locally? (pip install azdevrequired)python scripts/ci/test_index.py -qlocally? (pip install wheel==0.30.0required)For new extensions:
About Extension Publish
There is a pipeline to automatically build, upload and publish extension wheels.
Once your pull request is merged into main branch, a new pull request will be created to update
src/index.jsonautomatically.You only need to update the version information in file setup.py and historical information in file HISTORY.rst in your PR but do not modify
src/index.json.