Skip to content

Commit 85a4137

Browse files
authored
Merge pull request #106 from Azure/#103-multilb-config-validation
#103 multilb config validation
2 parents 1219117 + 6cf1a2c commit 85a4137

File tree

2 files changed

+98
-2
lines changed

2 files changed

+98
-2
lines changed

AzureBasicLoadBalancerUpgrade/module/AzureBasicLoadBalancerUpgrade/AzureBasicLoadBalancerUpgrade.psd1

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
RootModule = 'AzureBasicLoadBalancerUpgrade'
1313

1414
# Version number of this module.
15-
ModuleVersion = '2.4.3'
15+
ModuleVersion = '2.4.4'
1616

1717
# Supported PSEditions
1818
# CompatiblePSEditions = @()
@@ -107,7 +107,7 @@
107107
# IconUri = ''
108108

109109
# ReleaseNotes of this module
110-
ReleaseNotes = 'Fix missed VMSS backups in -multiLBConfig mode'
110+
ReleaseNotes = 'Enhanced -multiLBConfig validation to prevent incorrect useage'
111111

112112
# Prerelease string of this module
113113
# Prerelease = ''

AzureBasicLoadBalancerUpgrade/module/AzureBasicLoadBalancerUpgrade/modules/ValidateScenario/ValidateScenario.psm1

Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -547,6 +547,25 @@ Function Test-SupportedMultiLBScenario {
547547

548548
log -Message "[Test-SupportedMultiLBScenario] Verifying if Multi-LB configuration is valid for migration"
549549

550+
# check that backend type is not 'empty', meaning there is no reason to use -multiLBConfig
551+
log -Message "[Test-SupportedMultiLBScenario] Checking that backend type is not 'empty' for any of the multi load balancers"
552+
If ($multiLBConfig.scenario.backendType -contains 'Empty') {
553+
log -ErrorAction Stop -Severity 'Error' -Message "[Test-SupportedMultiLBScenario] One or more Basic Load Balancers backend is empty. Empty load balancer should not be included in -multiLBConfig. Use standalone migrations or remove the load balancer with the empty backend from the -multiLBConfig parameter"
554+
return
555+
}
556+
557+
# check that all backend pool members are VMs or VMSSes
558+
log -Message "[Test-SupportedMultiLBScenario] Checking that all backend pool members are VMs or VMSSes"
559+
$backendMemberTypes = ($multiLBConfig.scenario.BackendType | Sort-Object | Get-Unique)
560+
561+
If ($backendMemberTypes.count -gt 1) {
562+
log -ErrorAction Stop -Severity 'Error' -Message "[Test-SupportedMultiLBScenario] Basic Load Balancer backend pools can contain only VMs or VMSSes, contains: '$($backendMemberTypes -join ',')'"
563+
return
564+
}
565+
Else {
566+
log -Message "[Test-SupportedMultiLBScenario] All backend pool members are '$($backendMemberTypes)'"
567+
}
568+
550569
# check that standard load balancer names are different if basic load balancers are in the same resource group
551570
log -Message "[Test-SupportedMultiLBScenario] Checking that standard load balancer names are different if basic load balancers are in the same resource group"
552571

@@ -571,6 +590,83 @@ Function Test-SupportedMultiLBScenario {
571590
}
572591
}
573592

593+
# check that that the provided load balancer do share backend pool members - using -multiLBConfig when backend is not shared adds risk
594+
log -Message "[Test-SupportedMultiLBScenario] Checking that that the provided load balancer do share backend pool members - using -multiLBConfig when backend is not shared adds risk"
595+
596+
## shared backend should be a single VMSS
597+
If ($multiLBConfig[0].scenario.backendType -eq 'VMSS') {
598+
$basicLBBackends = @()
599+
ForEach ($config in $multiLBConfig) {
600+
$basicLBBackends += $config.BasicLoadBalancer.BackendAddressPools.BackendIpConfigurations.id | ForEach-Object {$_.split('/virtualMachines/')[0]}
601+
}
602+
$groupedBackends = $basicLBBackends | Sort-Object | Get-Unique
603+
604+
If ($groupedBackends.Count -gt 1) {
605+
log -Severity Error -Message "[Test-SupportedMultiLBScenario] The provided Basic Load Balancers do not share backend pool members (more than one backend VMSS found: '$($groupedBackends)'). Using -multiLBConfig when backend is not shared adds risk and complexity in recovery." -terminateOnError
606+
}
607+
Else {
608+
log -Message "[Test-SupportedMultiLBScenario] The provided Basic Load Balancers share '$($groupedBackends.count)' backend pool members."
609+
}
610+
}
611+
612+
## shared backend should be a single Availability Set for VMs
613+
If ($multiLBConfig[0].scenario.backendType -eq 'VM') {
614+
$nicIDs = @()
615+
ForEach ($basicLoadBalancer in $multiLBConfig.BasicLoadBalancer) {
616+
foreach ($backendAddressPool in $BasicLoadBalancer.BackendAddressPools) {
617+
foreach ($backendIpConfiguration in ($backendAddressPool.BackendIpConfigurations | Select-Object -Property Id -Unique)) {
618+
$nicIDs += "'$(($backendIpConfiguration.Id -split '/ipconfigurations/')[0])'"
619+
}
620+
}
621+
foreach ($inboundNatRule in $BasicLoadBalancer.inboundNatRules) {
622+
foreach ($backendIpConfiguration in ($inboundNatRule.BackendIpConfiguration | Select-Object -Property Id -Unique)) {
623+
$nicIDs += "'$(($backendIpConfiguration.Id -split '/ipconfigurations/')[0])'"
624+
}
625+
}
626+
}
627+
628+
$joinedNicIDs = $nicIDs -join ','
629+
630+
$graphQuery = @"
631+
resources |
632+
where type =~ 'microsoft.network/networkinterfaces' and id in~ ($joinedNicIDs) |
633+
project lbNicVMId = tolower(tostring(properties.virtualMachine.id)) |
634+
join ( resources | where type =~ 'microsoft.compute/virtualmachines' | project vmId = tolower(id), availabilitySetId = coalesce(properties.availabilitySet.id, 'NO_AVAILABILITY_SET')) on `$left.lbNicVMId == `$right.vmId |
635+
project availabilitySetId
636+
"@
637+
638+
log -Severity Verbose -Message "Graph Query Text: `n$graphQuery"
639+
640+
$waitingForARG = $false
641+
$timeoutStopwatch = [System.Diagnostics.Stopwatch]::StartNew()
642+
do {
643+
If (!$waitingForARG) {
644+
log -Message "[UpgradeVMPublicIP] Querying Resource Graph for availability sets of VMs in load balancers backend pools"
645+
}
646+
Else {
647+
log -Message "[UpgradeVMPublicIP] Waiting 15 seconds before querying ARG again (total wait time up to 15 minutes before failure)..."
648+
Start-Sleep 15
649+
}
650+
651+
$VMAvailabilitySets = Search-AzGraph -Query $graphQuery
652+
653+
$waitingForARG = $true
654+
} while ($VMPIPRecords.count -eq 0 -and $env:LBMIG_WAIT_FOR_ARG -and $timeoutStopwatch.Elapsed.Seconds -lt $global:defaultJobWaitTimeout)
655+
656+
If ($timeoutStopwatch.Elapsed.Seconds -gt $global:defaultJobWaitTimeout) {
657+
log -Severity Error -Message "[UpgradeVMPublicIP] Resource Graph query timed out before results were returned! The Resource Graph lags behind ARM by several minutes--if the resources to migrate were just created (as in a test), test the query from the log to determine if this was an ingestion lag or synax failure. Once the issue has been corrected follow the steps at https://aka.ms/basiclbupgradefailure to retry the migration." -terminateOnError
658+
}
659+
660+
# VMs must share an availability set or the backend must be a single VM with no availability set ('NO_AVAILABILITY_SET')
661+
If (($VMAvailabilitySets.availabilitySetId | Sort-Object | Get-Unique).count -gt 1 -or ($VMAvailabilitySets.availabilitySetId | Where-Object {$_ -eq 'NO_AVAILABILITY_SET'}).count -gt 1) {
662+
log -Severity Error -Message "[Test-SupportedMultiLBScenario] The provided Basic Load Balancers do not share backend pool members (VMs are in different or no Availability Sets: '$($VMAvailabilitySets.availabilitySetId -join ',')'). Using -multiLBConfig when backend is not shared adds risk and complexity in recovery." -terminateOnError
663+
}
664+
Else {
665+
log -Message "[Test-SupportedMultiLBScenario] The provided Basic Load Balancers share '$(($VMAvailabilitySets.availabilitySetId | Sort-Object | Get-Unique).count)' availability set"
666+
}
667+
}
668+
669+
574670
log -Message "[Test-SupportedMultiLBScenario] Multi-LB configuration is valid for migration"
575671
}
576672

0 commit comments

Comments
 (0)