Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Stop multiple Azure VMs at the same time using Azure PowerShell

Get-AzureRmVM -ResourceGroupName RG-VNETS | 
    ForEach-Object { 
        Get-AzureRmVM -ResourceGroupName RG-VNETS -Name $_.Name -Status 
    } | 
    ForEach-Object { 
        if (-Not ($_.Statuses[1].DisplayStatus -like "*deallocated*")) { 
            Stop-AzureRmVM -ResourceGroupName RG-VNETS -Name $_.Name -Force 
        } 
    }

I've got this script that stops all my Azure VMs, the catch here is that this script shuts down one VM at a time.

i.e. if I have three VMs: VM1, VM2, VM3

The script doesn't shut down VM2 until VM1 is fully shutdown and so on. I don't know if there's a way to tell PowerShell not to wait for each VM to be fully shutdown to proceed with the following one.

like image 371
miticoluis Avatar asked Sep 24 '16 13:09

miticoluis


1 Answers

There is already a feature request on GitHub for doing such operations asynchronously which should be implemented in the near future.

In the meantime you could do a workaround like the following using the PoshRSJob module - just replace temp4so with your resource group name

# Install PoshRSJob if necessary
#
# Install-Module PoshRSJob

Login-AzureRmAccount    

$start = Get-Date
$jobs = Get-AzureRmVM -ResourceGroupName temp4so | 
    % { 
        Get-AzureRmVM -ResourceGroupName temp4so -Name $_.Name -Status 
    } | 
    % { 
        if (-Not ($_.Statuses[1].DisplayStatus -like "*deallocated*")) { 
            $vm = $_
            Start-RSJob {               
                Stop-AzureRmVM -ResourceGroupName temp4so -Name ($using:vm).Name -Force
            }
        }
    }
$jobs | Wait-RSJob | Receive-RSJob
$jobs | Remove-RSJob
$end = Get-Date
Write-Host ("Stopping took {0}" -f ($end - $start))

which in my test case with 3 VMs resulted in output similar to the following which shows that the operations where done in parallel

OperationId : 
Status      : Succeeded
StartTime   : 24.09.2016 18:49:10
EndTime     : 24.09.2016 18:51:32
Error       : 

OperationId : 
Status      : Succeeded
StartTime   : 24.09.2016 18:49:11
EndTime     : 24.09.2016 18:51:22
Error       : 

OperationId : 
Status      : Succeeded
StartTime   : 24.09.2016 18:49:11
EndTime     : 24.09.2016 18:51:22
Error       : 

Stopping took 00:02:32.9115538

Note: You cannot simply use the standard Start-Job to offload the sync. operations to a background job as the newly created PowerShell instances in the background do not share the context with your initial session and therefore would require you to authenticate again for each of those sessions. As PoshRSJob uses PowerShell runspaces within the initial PowerShell instance it does not require to authenticate again.

like image 95
DAXaholic Avatar answered Nov 04 '22 00:11

DAXaholic