Public/New-AzVmSnapshot.ps1
function New-AzVmSnapshot { [CmdletBinding(SupportsShouldProcess, ConfirmImpact = 'High')] param ( [Parameter(Mandatory)] [ValidateNotNullOrEmpty()] [string[]]$VmName, [Parameter(Mandatory)] [ValidateNotNullOrEmpty()] [string]$ResourceGroupName ) foreach ($name in $VMName) { $scriptBlock = { param($ResourceGroupName, $VmName) $ErrorActionPreference = 'Stop' $snapshotName = "$VMName-$(Get-Date -UFormat '%Y%m%d%H%M%S')" $vm = Get-AzVm -ResourceGroup $ResourceGroupName -Name $VmName $stopParams = @{ ResourceGroupName = $ResourceGroupName Force = $true } try { Write-Verbose -Message "Stopping Azure VM [$($VmName)]..." $null = $vm | Stop-AzVm -ResourceGroupName $ResourceGroupName -Force $diskName = $vm.StorageProfile.OSDisk.Name $osDisk = Get-AzDisk -ResourceGroupName $ResourceGroupName -DiskName $diskname $snapConfig = New-AzSnapshotConfig -SourceUri $osDisk.Id -CreateOption Copy -Location $vm.Location Write-Verbose -Message "Creating snapshot..." $null = New-AzSnapshot -Snapshot $snapConfig -SnapshotName $snapshotName -ResourceGroupName $ResourceGroupName } catch { throw $_.Exception.Message } finally { Write-Verbose -Message "Starting Azure VM back up..." $null = $vm | Start-AzVm [pscustomobject]@{ 'VMName' = $VmName 'SnapshotName' = $snapshotName } } } $jobs = @() $jobs += Start-Job -ScriptBlock $scriptBlock -ArgumentList @($ResourceGroupName, $name) } Write-Verbose -Message 'Executed all snapshot operations. Waiting on jobs to finish...' $jobs | Wait-Job | Receive-Job } |