Thanks to various colleagues (Ori Amiga and Michael Washam) demonstrating this to me many months ago, I thought I would document how to create your own Virtual Machine (VM) on Windows Azure with 16 TB on demand, re-use it and then cleanup.

This demo should take you no more than 20 minutes from start to finish.

Before you start I’d recommend the following:

  1. Download and install the Windows Azure PowerShell Commandlets
  2. Download and install PowerGUI  (not mandatory but a great little tool for viewing parameters and running multiple scripts)
  3. Download and save your Windows Azure subscriptions publish settings 
  4. Download and install a Windows Azure storage explorer. I often use CloudXPlorer  as an example

I've split this demo into 6 sections. Each, of course, you could do in the portal or independently.

A> CREATE A QUICK VIRTUAL MACHINE

Copy the following script into PowerGUI, substituting your parameters to suit your preferences

# requires powershell for Azure (path may vary but likely to be the same as below)
Import-Module 'C:\Program Files (x86)\Microsoft SDKs\Windows Azure\PowerShell\Azure\Azure.psd1'

#import Azure settings
Import-AzurePublishSettingsFile -PublishSettingsFile "<yourlocation>.publishsettings"

#parameters to be change
#----------------------
$dclocation = ‘<DCName>’
$storageAccountName = ‘<StorageAccount>' 
$subscriptionName = '<StorageAccountName>'
$adminPassword = ‘<Password>’
$vmname = '<VmName>'
$cloudSvcName = '<CloudServiceName>'
#----------------------   #create or get storage account
$testStorage = Test-AzureName –torage $storageAccountName
if ($testStorage) {Get-AzureStorageAccount -StorageAccountName $storageAccountName}
else {New-AzureStorageAccount -StorageAccountName $storageAccountName -Location $dclocation}   
#use storage with subscription (name should really be automated)
Set-AzureSubscription -SubscriptionName $subscriptionName -CurrentStorageAccount $storageAccountName
Select-AzureSubscription -SubscriptionName $subscriptionName

# define the VM image parameters (uses Windows Server 2012
Test-AzureName -Service $cloudSvcName
$image = 'MSFT__Windows-Server-2012-Datacenter-201208.01-en.us-30GB.vhd'
   # create the VM (Using ExtraLarge so we can use upto 16 drives)
New-AzureQuickVM -Windows -ServiceName $cloudSvcName -Name $vmname -ImageName $image -Password $adminPassword -InstanceSize 'ExtraLarge' -Location $dclocation   # Start VM
Start-AzureVM -ServiceName $cloudSvcName -Name $vmname 
 
B> ADD DISKS TO YOUR VIRTUAL MACHINE

In this example the Powershell creates 16 disks 1000GB in size (1TB is the maximum size per Windows Azure Storage BLOB)

$vm = Get-AzureVM -Name $vmname -ServiceName $cloudSvcName

for($i = 1; $i -lt 16; $i++) 
{
    $diskname = "datadisk" + $i.ToString() 
    Add-AzureDataDisk -VM $vm -CreateNew -DiskSizeInGB 100 -DiskLabel $diskname -LUN $i 
}        
$vm | Update-AzureVM
 
C> CREATE VIRTUAL MACHINE STRIPED VOLUME

From the Windows Azure portal, go to Virtual Machines and select your VM. At the bottom of the screen select CONNECT

image 

When connected to your machine, using the password you used earlier in step A, navigate to the start page and type Disk Management tool running it.

Attach all the disks.

Select a single disk and then select the menu option for Create Striped Volume. Make sure you select quick format or you could be waiting a long time.

image

The disks will now be formatted and striped into a single volume in the drive letter you choose.

image

Once complete your extra drive in explorer with up to 16TB (depending on how many disks you added in step B)

image 

 

D> CLEANUP YOUR SERVICE

You have choices in terms of cleanup. Either removing the deployment outright, the specific VM or removing disks…

Removing the disks from your virtual machine (based on a size of 1000)

$origVM = get-azurevm -ServiceName $CloudServiceName

$disksToDetach = Get-AzureDisk | where {$_.DiskSizeInGB -eq 1000}
$disksToDetach | foreach { Remove-AzureDataDisk -vm $origVM -LUN $_.LUN}
$orig | Update-AzureVM

Removing the virtual machine:

#stop the VM
Stop-AzureVM -ServiceName $cloudSvcName -Name $cloudSvcName 

#remove the VM - This process doesn’ delete the underlying .vhd files of the disks mounted on that virtual machine.
Remove-AzureVM -ServiceName $cloudSvcName  -Name $cloudSvcName  
Removing the deployments:

# Faster way of removing all VMs while keeping the cloud service/DNS name  
Remove-AzureDeployment -ServiceName $cloudSvcName -Slot Production –Force 
 

E> DISK REATTACH

Once you have removed your disks you may want to reuse the disks by reattaching the disks to a new VM (based on a size of 1000)

Select-AzureSubscription $subscriptionName
$disks = Get-AzureDisk | Where-Object {$_.DiskSizeInGB -eq 1000 }


for($i = 0; $i -lt $disks.Length; $i++)
{
    Get-AzureVM $CloudSvcName -Name $vmName | Add-AzureDataDisk -Import -DiskName $disks[$i].DiskName -LUN $i | Update-AzureVM
}

Now you can re-login to your virtual machine, go to disk management and re add your disks by right clicking and selecting Import Foreign Disks

image 

As a developer I think this feature of moving around machines and large amounts of data, whilst maintaining state and data integrity is, simply, awesome.

 

F> DISK CLEANUP

Ok, you just cleaned up the virtual machines, disks and service deployments but, by design you didn't really cleanup the disks. I could have included that in one script BUT I wanted to make sure of a couple of things. First, that the disks (OS and data) can be reattached very easily, regardless of removing the service and virtual machine. Second that if you did save data to those disks that you were not going to lose it!

So with those caveats aside, this script will remove the disks! (based on a size of 1000) and you are back to the demo start state.

$disksToDetach = Get-AzureDisk | where {$_.DiskSizeInGB -eq 1000}
$disksToDetach |  foreach { Remove-AzureDisk -DiskName $_.DiskName –DeleteVHD}

Check in the portal for confirmation and using your storage tool that you are back to where you started!

 

Links:

Automating Windows Azure Virtual Machines with PowerShell

Windows Azure PowerShell documentation

 

(special thanks too to Ken Faulkner for error checking my poor PowerShell skills)