Renaming Virtual Machine Disks


pexels-photo-208637[1]Let’s say we would like to rename disks on a Virtual Machine (VM).  Here we mean renaming the Azure Resource Name of the managed disk.  How would we go about that?

Why would we want to?  Primarily to get our internal nomenclature right.  A typical example is when we do migrate from unmanaged to managed disk (see article here) using the ConvertTo-AzureRmVMManagedDisk command.  This command converts all disks from page blobs to managed disks ; it gives the managed disks the name of the page blob and prepend the name of the VM.  That might not be your nomenclature & there is no way to override the names.

Nomenclature / naming convention is important if only to ensure clarity for human operators.

The Challenge

Our first challenge is that disks, like most Azure resources, can’t be renamed.  There is no such command.  For instance, if we look at Update-AzureRmDisk, it takes a disk object and the disk name is read only.

So we’ll need to actually copy the disks to change their names:  good old copy then delete the original scheme.

Our second challenge is that, as we’ve seen with the Virtual Machine anatomy, although data disks can be added and removed on the fly, the OS disk (i.e. primary disk) cannot.  That means we cannot swap the OS Disk to another disk.

We’ll need to recreate the VM to make it point to the disk copy with a new name.

So much for renaming, right?

The Solution

The solution we lay out here is based on ARM template.  You could accomplish something similar using PowerShell or Command Line Interface (CLI) scripts.

A demo of the solution is available on GitHub.  It deploys a Linux VM behind a public load balancer with SSH being routed to the VM.  In order to fully explore the demo, we need to initializes the data disks.

In general, the solution follows five steps:

  1. Determine the Virtual Machine ARM template
  2. Delete the Virtual Machine
  3. Copy disks with new names
  4. Re-create the Virtual Machine and attach to disk copies
  5. Delete original disks

Determine the Virtual Machine ARM template

Since we’ll recreate the VM using ARM template, we need to determine the ARM Template of the VM.

If we already have it because we proceed with ARM template in general, then done.  Otherwise we need to work a little bit.

The best approach usually is to use the Automation Script option on the left hand side menu of either the VM or its resource group.

image

From there we can find the node for our VM and then mechanically we can clean up the template.

We do not need the template for the entire resource group.  We only need the template for the VM itself (not its NICs or VNET, etc.).

Delete the Virtual Machine

Let’s delete the Virtual Machine to better recreate it.

We will use a PowerShell command.  Using the Azure Portal would yield the same result.


$rgName = 'ren' # or the Resource Group name we use
$vmName = 'Demo-VM'    # or the name of the VM we use
Remove-AzureRmVM -Force -ResourceGroupName $rgName -Name $vmName

Of course, we need to replace the variable with values corresponding to our case at hand.

This deletes the VM but leaves all its artefact behind:  VNET, Public IP, NIC, Disks, etc.  .  We’ll be able to attach back to those.

Copy disks with new names

We’re going to use a new ARM template to copy disks.  Here is our demo solution’s template.

Basically, the ARM templates create new disks using the creationOption value copy, pointing to the original disk of the VM.

For the demo solution, we use a fancy trick where we map the old and new disk name in a variable:


"disks": [
  {
    "oldName": "Demo-VM-OS",
    "newName": "Clone-Demo-OS"
  },
  {
    "oldName": "Demo-VM-data2",
    "newName": "Clone-Demo-data2"
  },
  {
    "oldName": "Demo-VM-data3",
    "newName": "Clone-Demo-data3"
  }
]

and then we use a copy construct to loop to the JSON array:


    {
      "comments": "Copy existing disks in order to change their names",
      "apiVersion": "2017-03-30",
      "copy": {
        "name": "snapshot-loop",
        "count": "[length(variables('disks'))]"
      },
      "type": "Microsoft.Compute/disks",
      "name": "[variables('disks')[copyIndex()].newName]",
      "location": "[resourceGroup().location]",
      "sku": {
        "name": "Premium_LRS"
      },
      "properties": {
        "creationData": {
          "createOption": "copy",
          "sourceUri": "[resourceId('Microsoft.Compute/disks', variables('disks')[copyIndex()].oldName)]"
        }
      }
    },


One of the advantage of using ARM templates to copy the disks is that the copy is parallelized:  in the case of our demo solution, we have 3 disks and they are copied in parallel instead of one after.  The is of course faster.

Re-create the Virtual Machine and attach to disk copies

In the same ARM template, we can recreate the VM.  This is what we do in our demo solution’s template by adding a dependency on the disks.

The VM is recreated by attaching to the disk copies.  Similarly, it links back to its NIC.

Delete original disks

At this point we did “rename the disks”.  We just have some cleanups to do with the original disks.

We simply delete them:


$rgName = ‘ren’ # or the Resource Group name you used
$oldDisks = 'Demo-VM-OS', 'Demo-VM-data2', 'Demo-VM-data3'

$oldDisks | foreach {Remove-AzureRmDisk -ResourceGroupName $rgName -Force -DiskName $_}

Again, replacing the first two variables by what make sense in our use case.

Summary

We did come up with a recipe to rename managed disks by copying them and attaching the copies to a recreated VM.

Our demo example had a lot of specifics:

  • It’s a Linux VM (Windows would be very similar)
  • It’s exposed through a load balancer on a public IP (this doesn’t matter, only its NIC matter ; the NIC is the one being load balanced)
  • It had 2 data disks

The solution would change depending on the specifics of the VM but the same steps would apply.

Advertisements

One thought on “Renaming Virtual Machine Disks

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s