Azure VMs

1 Information about Virtual Machines
2 Remote Access to a VM
2.1 RDP
2.2 Access to a VM with WinRM and SSL-Encryption
3 Processing VMs
3.1 Creating VMs
3.2 Stopping and Starting VMs
3.2.1 Stopping VMs - Deallocation
3.2.2 Starting VMs
4 Virtual Disks
4.1 Attaching an additional disk
4.2 Getting disk information
 

1. Information about Virtual Machines

Under the submenu "VIRTUAL MACHINES" of the Azure Portal all virtual machines of the current subscription can bei found.

 

Example 1: Get Information about a specific Virtual Machine

$ServiceName = "PsPraxis1"
$Name = "PPVM01"
 
Get-AzureVM -ServiceName $ServiceName -Name $Name `
    | Format-List Name, IpAddress, Powerstate, ServiceName
#possible output

Name        : ppVM01
IpAddress   : 10.76.190.185
PowerState  : Started
ServiceName : PsPraxis1

 

Endpoints are needed for remote access which is going to be shown later

 

Example 2: Get Endpoints of a specific Virtual Machine

Function Main{
  $ServiceName = "PsPraxis1"
  $Name = "PPVM01"
  Get-Endpoints $ServiceName $Name
}
 
Function Get-Endpoints{
  Param($ServiceName, $Name)
  Get-AzureVM -ServiceName $ServiceName -Name $Name `
     | Get-AzureEndpoint | Select Name,Localport,Port    
}
 
Main
#possible output

Name           LocalPort  Port
----           ---------  ----
PowerShell          5986  5986
Remote Desktop      3389 53836

 

2. Remote Access to a VM
2.1 RDP

A RDP-Connection can be easily established with the CONNECT button

 

Example 1: Download or launch a RDP-Connection file

Function Main{
  $ServiceName = "PsPraxis1"
  $Name = "PPVM01"
  Get-Access $ServiceName $Name
}
 
Function Get-Access{
  Param($ServiceName, $Name)
  Get-AzureRemoteDesktopfile -ServiceName $ServiceName -Name $Name -Launch
  #Get-AzureRemoteDesktopfile -ServiceName $ServiceName -Name $Name -LocalPath "c:\temp" 
}
 
Main

 

2.2 Access to a VM with WinRM and SSL-Encryption

Naturally for SSL-encryption a SSL-certificate on the remote computer and its fitting Root Certificate on the remoting (On premise) computer is needed. For non productive purpose a self signed certificate issued for your Cloud Service has been already created by Azure. This self signed certificate can be used for both Root Certificate and SSL encryption. The certificate can be found on all of your Virtual Machines and must only be exported and copied to the Root Certificates container of your remoting computer .
 

The self-signed certificate is located in the VM's Computer-Personal certificate container, from where it can be exported as *.cer file (of course without its private key).

The Personal-Container of a Virtual Machine in your Azure Cloud Service (e.g. PSPraxis1)

Subsequently the exported certificate must be still imported in the "Trusted Root Certication" container


Together with the found endpoints above (see example 1b) the SSL-Connection can easily opened
 

Function Main{
  $ServiceName = "PsPraxis1"
  $Name = "PPVM01"
  #Get-Info $ServiceName $Name
  Get-SSLAccess $ServiceName $Name
}
 
Function Get-SSLAccess{
  Param($ServiceName, $Name)
 
  #$Port = 55691
  $Port = 5986
  Enter-PSSession -computername "pspraxis1.cloudapp.net" -Port $port -Credential myadmin -UseSSL
}
 
Main

After completion of your credentials the powershell command line of the Azure VM will appear

[pspraxis1.cloudapp.net]: PS C:\Users\myadmin\Documents> $env:Computername
PPVM01

Other commands like "Get-Service" or complete scripts can be executed until an "Exit" or "Exit-PsSession" will end the remote connection


The certificate can also be downloaded by browsers like Firefox or Chrome.
E.g. in Chrome put in "https://<Cloud Service>:<Endpoint>" in the addressline

Consequently this certificate has to be imported to the "Trusted Root Certificate" container of the onpremis computer as shown above. The process in Firefox is very similar.

 

3 Processing Virtual Machines
3.1 Creating Virtual Machines

Example 1: Creating a simple VM with New-AzureQuickVM (Storageaccount and CloudService do already exist)

Set-StrictMode -Version "2.0"
Clear-Host
 
Function Main{
  $Name = "VM01"
  $AdminUser = "myAdmin"
  $Password = "Hola123Hola"
 
  #use lowercase letters
  $Storagename = "storage001z" 
  
  #Get-AzureService | Select ServiceName
  $ServiceName = "CloudService001z"
 
  #Get-AzureLocation | Select DisplayName
  #only required, if the Cloud Service does not yet exist
  $Location = "North Europe"
    
  #Show-ImageFamilies
  $ImageFamily = "Windows Server 2012 R2 Datacenter"
  
  #(Get-AzureRolesize).InstanceSize
  $Size = "Small"
  
  $ImageName = Get-LastImageName
 
  New-VM $ServiceName $Storagename $Location $Name $ImageName $AdminUser $Password $Size
}#end Function Main
 
 
Function New-VM{
 #Creates a virtualmachine
 #CloudServiceName must already exist!
 #StorageAccount must already exist!
 
 Param($ServiceName,$StorageName,$Location,$Name,$Imagename,$AdminUser,$Password,$Size)
 
 $SubscriptionName = (Get-AzureSubscription).SubscriptionName
 Set-AzureSubscription -SubscriptionName $SubscriptionName -CurrentStorageAccountName $StorageName
 
 New-AzureQuickVM -Windows `
          -ServiceName $ServiceName `
          -Name $Name `
          -ImageName $ImageName `
          -AdminUsername $adminUser `
          -Password $Password  `
          -InstanceSize $Size
          #-Location would be required, if servicename does not yet exist
 }
 
Function Get-LastImageName{
  $ImageFamily = "Windows Server 2012 R2 Datacenter"
 
  $ImageName = Get-AzureVMImage | Where { $_. ImageFamily -eq $imageFamily } 
  $ImageName  = $ImageName |  Sort PublishedDate -Descending 
  $ImageName  = $ImageName  | Select -ExpandProperty ImageName -First 1
  Return $ImageName
}
 
Main
#possible output

OperationDescription OperationId                          OperationStatus
-------------------- -----------                          ---------------
New-AzureQuickVM     d75fcfd4-a4e6-1637-aa37-70658bbbc9be Succeeded      

 

3.2 Stopping and Starting VMs

Concurrent stop/start of VMs in the same cloud service does not work. That kind of operation requires an exclusive access to the cloud service resources! 
 

3.2.1 Stopping Azure Machines (Deallocation)

The cmdlet "Stop-AzureVM" contains three options

Example 1a:Stop and Deallocate a VM  

Stop-AzureVM -ServiceName "rangervm001" -Name "rangervm001"


Example 1b:Stop but do not Deallocate a VM

Stop-AzureVM -ServiceName "rangervm001" -Name "rangervm001" -StayProvisioned


Example 1c:Stop and Deallocate a VM - No prompt if its the last VM

Stop-AzureVM -ServiceName "rangervm001" -Name "rangervm001" -Force 


Example 2: Stopping VMs one after another

Set-StrictMode -Version "2.0"
Clear-Host
 
Function Main{
  Stop-AllVMs
}
 
Function Stop-AllVMs{
  $VMs = @(Get-AzureVM)
  ForEach ($VM in $VMs){
    If ($VM.PowerState -eq "Started"){
     Write-Host "`nStopping $($VM.Name)" -backgroundcolor green -foregroundcolor yellow
     Stop-AzureVM -ServiceName $VM.ServiceName -Name $VM.Name -force
     Write-Host "$($VM.Name) has been stopped" -backgroundcolor green -foregroundcolor yellow
   }Else{
     Write-Host "`n`"Powerstate`" of $($VM.Name) is not `"Started`". `
     $($VM.Name) has not been stpped" -BackgroundColor Yellow -ForegroundColor Red 
      }#if 
   }#Foreach
} #Stop-AllVMs
 
Main
#possible output

Stopping VM01
OperationDescription                          OperationId                                  OperationStatus
--------------------                          -----------                                  --------------- 
Stop-AzureVM                                  04a6c172-b704-112a-b71c-d0590765d325         Succeeded
VM01 has been stopped
 
Stopping VM02
Stop-AzureVM                                  dd2b75b1-5dbc-1b18-9280-f09fb612812e         Succeeded 
VM02 has been stopped

It takes a few minutes until each machine will be started one after another. Meanwhile the Powershell is busy and cannot be used. To have the Powershell faster again available, the following oneline using Powershell-Job can be used.

Example 3a: Stopping Azure Machines using a Powershell Job

Start-Job -Name "Stop" -ScriptBlock { Get-AzureVM | `
    ?{ $_.PowerState -eq "Started" } | Stop-AzureVM -Force }
#possible output

Id     Name            PSJobTypeName   State         HasMoreData     Location                 
--     ----            -------------   -----         -----------     --------               
2      Test            BackgroundJob   Running       True            localhost

 

Example 3b: Stopping Azure Machines using a Powershell Job 

Set-StrictMode -Version "2.0"
Clear-Host

Start-Job -Name "StopJob" -ScriptBlock {
  $Exceptions = @("VM02","VM05")
  #$Exceptions = @()
  $VMs = @(Get-AzureVM) | Where {$_.Name -NotIn $Exceptions}
  $VMs | ?{ $_.PowerState -eq "Started" } | Stop-AzureVM -force
}


Using Powershell-Jobs no information can be seen. To watch the current status the following command can be used
Example 4: Watching the Powerstate of VMs

Get-AzureVM | Format-Table Name, Powerstate -AutoSize
#possible output

Name PowerState
---- ----------
VM01 Started   
VM02 Stopped   
VM04 Stopped   
VM05 Stopped

 

3.2.2 Starting Azure Machines

 

Set-StrictMode -Version "2.0"
Clear-Host
 
Function Main{
  Start-AllVMs
}
 
Function Start-AllVMs{
  $VMs = @(Get-AzureVM)
  
  ForEach ($VM in $VMs){
      If ($VM.PowerState -eq "Stopped"){
        Write-Host "`nStarting $($VM.Name)" -backgroundcolor green -foregroundcolor yellow
        Start-AzureVM -ServiceName $VM.ServiceName -Name $VM.Name 
        Write-Host "$($VM.Name) has been started" -backgroundcolor green -foregroundcolor Yellow
      }Else{
        Write-Host "`n`"Powerstate`" of $($VM.Name) is not `"Stopped`". `
          $($VM.Name) has not been started" -BackgroundColor Yellow -ForegroundColor Red 
      }#if 
     }#Foreach
 } #Start-AllVMs
 
 Main

 

Example: Starting Azure Machines using Powershell JobsThe use of Powershell-Job is described in the chapter above.

Start-Job -StartVMs "Test" -ScriptBlock { Get-AzureVM | `
    ?{ $_.PowerState -eq “Stopped” } | Start-AzureVM }
#possible output

Id     Name            PSJobTypeName   State         HasMoreData     Location                 
--     ----            -------------   -----         -----------     --------               
2      StartVMs        BackgroundJob   Running       True            localhost

 

Set-StrictMode -Version "2.0"
Clear-Host

Start-Job -Name "StartJob" -ScriptBlock {
  #$Exceptions = @()
  $Exceptions = @("VM01","VM02")
   $VMs = @(Get-AzureVM) | Where {$_.Name -NotIn $Exceptions}
  $VMs | ?{ $_.PowerState -eq "Stopped" } | Start-AzureVM
}

 

4 Virtual Disks

4.1 Adding a new Data Disk

 

Example: Adding a new data disk to a virtual machine

Set-StrictMode -Version "2.0"
Clear-Host
 
$VMName = "VM02"
$ServiceName = "CloudService001z"
$DisksizeInGB = 1
$Label = "DataDisk1"
$StorageAccount = "storage001z"
$DiskName = "VM02-DD1"
$Medialocation = "https://$StorageAccount.blob.core.windows.net/vhds/$DiskName.vhd"
$Lun = 1 #DiskNumber
 
$VM = Get-AzureVM -Name $VMName -ServiceName $ServiceName
$VM = $VM | Add-AzureDataDisk -CreateNew -DisksizeinGB $DisksizeInGB -Disklabel $Label -LUN $Lun `
                                                        -Medialocation $Medialocation 
$VM | Update-AzureVM
#possible output

OperationDescription OperationId                          OperationStatus
-------------------- -----------                          ---------------
Update-AzureVM       a19d3f69-9503-117b-b2b4-0d3d57e9c2dd Succeeded 

A correct value for the variable "$Medialocation" can be found with the disk information shown in the next chapter "Getting disk information"

 

4.2 Getting disk information

In the Azure Portal it can be a little bit hard to find out, which disk is attached to which Virtual Machine, especially in case of several machines used with several additionally attached disks.Azure-Powershell provides the cmdlet "Get-AzureDisk" that gives back a lot of information for each used disk. It is not difficult to get a neat overview with only some easy adptions.
 

Example 1: Overview of used disks

Function Main{
  Get-Disks | Fl * 
}
 
Function Get-Disks{
  $AllDisks = @()
  $AzureDisks = Get-AzureDisk
  ForEach ($AzureDisk in $AzureDisks){
    [PsObject]$Disk = "" | Select VMName,OS,DiskName,Medialink
    $Disk.VMName = ($AzureDisk).Attachedto.Rolename
    $Disk.OS = $AzureDisk.OS
    $Disk.DiskName = $AzureDisk.DiskName
    $Disk.MediaLink = $AzureDisk.MediaLink
    $AllDisks += $Disk
  }#ForEach
  Return ,$AllDisks
}#End Function
 
Main
#possible output

VMName    : VM04
OS        : Windows
DiskName  : Cloudservice001z-VM04-0-201509172002560316
Medialink : https://storage001z.blob.core.windows.net/vhds/Srv001z-VM04-2015-9-17-22-2-43-661-0.vhd
 
VMName    : VM05
OS        : Windows
DiskName  : Cloudservice001z-VM05-0-201509172025520207
Medialink : https://storage001z.blob.core.windows.net/vhds/Srv001z-VM05-2015-9-17-22-25-41-589-0.vhd
 
VMName    : VM05
OS        :    
DiskName  : Cloudservice001z-VM05-0-201509220844090623
Medialink : https://storage001z.blob.core.windows.net/vhds/Srv001z-VM05-0922-1.vhd

As you can see "VM05" has two disks: one operational disk (OS: Windows) and one data disk (OS:  )

 

As well as with Powershell the same information of "Get-AzureDisk" can be found in the portal:

To find this site: Storage  -> <Storagename> -> CONTAINERS -> vhds