Skip to content

Commit 621aa1c

Browse files
azure-sdkbenbp
andauthored
Sync eng/common directory with azure-sdk-tools for PR 5242 (Azure#28508)
* Consolidate naming logic and generate short hash names for local use * Shorten long lines * Handle issues with EnvironmentVariable parameter ref being updated * Warn on env variable overwrite. Base name generation off resource group * Use SHA256 algorithm for short name hash --------- Co-authored-by: Ben Broderick Phillips <[email protected]>
1 parent 0bdbd6b commit 621aa1c

File tree

4 files changed

+109
-61
lines changed

4 files changed

+109
-61
lines changed

eng/common/TestResources/New-TestResources.ps1

Lines changed: 58 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -260,7 +260,7 @@ function BuildBicepFile([System.IO.FileSystemInfo] $file)
260260
return $templateFilePath
261261
}
262262

263-
function BuildDeploymentOutputs([string]$serviceName, [object]$azContext, [object]$deployment) {
263+
function BuildDeploymentOutputs([string]$serviceName, [object]$azContext, [object]$deployment, [hashtable]$environmentVariables) {
264264
$serviceDirectoryPrefix = BuildServiceDirectoryPrefix $serviceName
265265
# Add default values
266266
$deploymentOutputs = [Ordered]@{
@@ -277,7 +277,7 @@ function BuildDeploymentOutputs([string]$serviceName, [object]$azContext, [objec
277277
"AZURE_SERVICE_DIRECTORY" = $serviceName.ToUpperInvariant();
278278
}
279279

280-
MergeHashes $EnvironmentVariables $(Get-Variable deploymentOutputs)
280+
MergeHashes $environmentVariables $(Get-Variable deploymentOutputs)
281281

282282
foreach ($key in $deployment.Outputs.Keys) {
283283
$variable = $deployment.Outputs[$key]
@@ -293,8 +293,15 @@ function BuildDeploymentOutputs([string]$serviceName, [object]$azContext, [objec
293293
return $deploymentOutputs
294294
}
295295

296-
function SetDeploymentOutputs([string]$serviceName, [object]$azContext, [object]$deployment, [object]$templateFile) {
297-
$deploymentOutputs = BuildDeploymentOutputs $serviceName $azContext $deployment
296+
function SetDeploymentOutputs(
297+
[string]$serviceName,
298+
[object]$azContext,
299+
[object]$deployment,
300+
[object]$templateFile,
301+
[hashtable]$environmentVariables = @{}
302+
) {
303+
$deploymentEnvironmentVariables = $environmentVariables.Clone()
304+
$deploymentOutputs = BuildDeploymentOutputs $serviceName $azContext $deployment $deploymentEnvironmentVariables
298305

299306
if ($OutFile) {
300307
if (!$IsWindows) {
@@ -316,13 +323,20 @@ function SetDeploymentOutputs([string]$serviceName, [object]$azContext, [object]
316323
Log "Persist the following environment variables based on your detected shell ($shell):`n"
317324
}
318325

326+
# Write overwrite warnings first, since local execution prints a runnable command to export variables
327+
foreach ($key in $deploymentOutputs.Keys) {
328+
if ([Environment]::GetEnvironmentVariable($key)) {
329+
Write-Warning "Deployment outputs will overwrite pre-existing environment variable '$key'"
330+
}
331+
}
332+
319333
# Marking values as secret by allowed keys below is not sufficient, as there may be outputs set in the ARM/bicep
320334
# file that re-mark those values as secret (since all user-provided deployment outputs are treated as secret by default).
321335
# This variable supports a second check on not marking previously allowed keys/values as secret.
322336
$notSecretValues = @()
323337
foreach ($key in $deploymentOutputs.Keys) {
324338
$value = $deploymentOutputs[$key]
325-
$EnvironmentVariables[$key] = $value
339+
$deploymentEnvironmentVariables[$key] = $value
326340

327341
if ($CI) {
328342
if (ShouldMarkValueAsSecret $serviceName $key $value $notSecretValues) {
@@ -347,7 +361,7 @@ function SetDeploymentOutputs([string]$serviceName, [object]$azContext, [object]
347361
}
348362
}
349363

350-
return $deploymentOutputs
364+
return $deploymentEnvironmentVariables, $deploymentOutputs
351365
}
352366

353367
# Support actions to invoke on exit.
@@ -400,17 +414,13 @@ try {
400414
exit
401415
}
402416

403-
$UserName = GetUserName
404-
405-
if (!$BaseName) {
406-
if ($CI) {
407-
$BaseName = 't' + (New-Guid).ToString('n').Substring(0, 16)
408-
Log "Generated base name '$BaseName' for CI build"
409-
} else {
410-
$BaseName = GetBaseName $UserName (GetServiceLeafDirectoryName $ServiceDirectory)
411-
Log "BaseName was not set. Using default base name '$BaseName'"
412-
}
413-
}
417+
$serviceName = GetServiceLeafDirectoryName $ServiceDirectory
418+
$BaseName, $ResourceGroupName = GetBaseAndResourceGroupNames `
419+
-baseNameDefault $BaseName `
420+
-resourceGroupNameDefault $ResourceGroupName `
421+
-user (GetUserName) `
422+
-serviceDirectoryName $serviceName `
423+
-CI $CI
414424

415425
# Make sure pre- and post-scripts are passed formerly required arguments.
416426
$PSBoundParameters['BaseName'] = $BaseName
@@ -546,19 +556,8 @@ try {
546556
$ProvisionerApplicationOid = $sp.Id
547557
}
548558

549-
$serviceName = GetServiceLeafDirectoryName $ServiceDirectory
550-
551-
$ResourceGroupName = if ($ResourceGroupName) {
552-
$ResourceGroupName
553-
} elseif ($CI) {
554-
# Format the resource group name based on resource group naming recommendations and limitations.
555-
"rg-{0}-$BaseName" -f ($serviceName -replace '[\.\\\/:]', '-').ToLowerInvariant().Substring(0, [Math]::Min($serviceName.Length, 90 - $BaseName.Length - 4)).Trim('-')
556-
} else {
557-
"rg-$BaseName"
558-
}
559-
560559
$tags = @{
561-
Owners = $UserName
560+
Owners = (GetUserName)
562561
ServiceDirectory = $ServiceDirectory
563562
}
564563

@@ -581,7 +580,6 @@ try {
581580
# to determine whether resources should be removed.
582581
Write-Host "Setting variable 'CI_HAS_DEPLOYED_RESOURCES': 'true'"
583582
LogVsoCommand "##vso[task.setvariable variable=CI_HAS_DEPLOYED_RESOURCES;]true"
584-
$EnvironmentVariables['CI_HAS_DEPLOYED_RESOURCES'] = $true
585583
}
586584

587585
Log "Creating resource group '$ResourceGroupName' in location '$Location'"
@@ -592,16 +590,17 @@ try {
592590
if ($resourceGroup.ProvisioningState -eq 'Succeeded') {
593591
# New-AzResourceGroup would've written an error and stopped the pipeline by default anyway.
594592
Write-Verbose "Successfully created resource group '$($resourceGroup.ResourceGroupName)'"
595-
}
596-
elseif (!$resourceGroup) {
593+
} elseif (!$resourceGroup) {
597594
if (!$PSCmdlet.ShouldProcess($resourceGroupName)) {
598595
# If the -WhatIf flag was passed, there will be no resource group created. Fake it.
599596
$resourceGroup = [PSCustomObject]@{
600597
ResourceGroupName = $resourceGroupName
601598
Location = $Location
602599
}
603600
} else {
604-
Write-Error "Resource group '$ResourceGroupName' already exists." -Category ResourceExists -RecommendedAction "Delete resource group '$ResourceGroupName', or overwrite it when redeploying."
601+
Write-Error "Resource group '$ResourceGroupName' already exists." `
602+
-Category ResourceExists `
603+
-RecommendedAction "Delete resource group '$ResourceGroupName', or overwrite it when redeploying."
605604
}
606605
}
607606

@@ -623,7 +622,10 @@ try {
623622
$displayName = "$($baseName)$suffix.$ResourceType-resources.azure.sdk"
624623
}
625624

626-
$servicePrincipalWrapper = NewServicePrincipalWrapper -subscription $SubscriptionId -resourceGroup $ResourceGroupName -displayName $DisplayName
625+
$servicePrincipalWrapper = NewServicePrincipalWrapper `
626+
-subscription $SubscriptionId `
627+
-resourceGroup $ResourceGroupName `
628+
-displayName $DisplayName
627629

628630
$global:AzureTestPrincipal = $servicePrincipalWrapper
629631
$global:AzureTestSubscription = $SubscriptionId
@@ -650,7 +652,8 @@ try {
650652
}
651653
}
652654
catch {
653-
Write-Warning "The Object ID of the test application was unable to be queried. You may want to consider passing it explicitly with the 'TestApplicationOid` parameter."
655+
Write-Warning "The Object ID of the test application was unable to be queried. " + `
656+
"You may want to consider passing it explicitly with the 'TestApplicationOid` parameter."
654657
throw $_.Exception
655658
}
656659

@@ -667,7 +670,11 @@ try {
667670
# If the role hasn't been explicitly assigned to the resource group and a cached service principal is in use,
668671
# query to see if the grant is needed.
669672
if (!$resourceGroupRoleAssigned -and $AzureTestPrincipal) {
670-
$roleAssignment = Get-AzRoleAssignment -ObjectId $AzureTestPrincipal.Id -RoleDefinitionName 'Owner' -ResourceGroupName "$ResourceGroupName" -ErrorAction SilentlyContinue
673+
$roleAssignment = Get-AzRoleAssignment `
674+
-ObjectId $AzureTestPrincipal.Id `
675+
-RoleDefinitionName 'Owner' `
676+
-ResourceGroupName "$ResourceGroupName" `
677+
-ErrorAction SilentlyContinue
671678
$resourceGroupRoleAssigned = ($roleAssignment.RoleDefinitionName -eq 'Owner')
672679
}
673680

@@ -677,12 +684,18 @@ try {
677684
# the explicit grant.
678685
if (!$resourceGroupRoleAssigned) {
679686
Log "Attempting to assigning the 'Owner' role for '$ResourceGroupName' to the Test Application '$TestApplicationId'"
680-
$principalOwnerAssignment = New-AzRoleAssignment -RoleDefinitionName "Owner" -ApplicationId "$TestApplicationId" -ResourceGroupName "$ResourceGroupName" -ErrorAction SilentlyContinue
687+
$principalOwnerAssignment = New-AzRoleAssignment `
688+
-RoleDefinitionName "Owner" `
689+
-ApplicationId "$TestApplicationId" `
690+
-ResourceGroupName "$ResourceGroupName" `
691+
-ErrorAction SilentlyContinue
681692

682693
if ($principalOwnerAssignment.RoleDefinitionName -eq 'Owner') {
683694
Write-Verbose "Successfully assigned ownership of '$ResourceGroupName' to the Test Application '$TestApplicationId'"
684695
} else {
685-
Write-Warning "The 'Owner' role for '$ResourceGroupName' could not be assigned. You may need to manually grant 'Owner' for the resource group to the Test Application '$TestApplicationId' if it does not have subscription-level permissions."
696+
Write-Warning "The 'Owner' role for '$ResourceGroupName' could not be assigned. " + `
697+
"You may need to manually grant 'Owner' for the resource group to the " + `
698+
"Test Application '$TestApplicationId' if it does not have subscription-level permissions."
686699
}
687700
}
688701

@@ -773,7 +786,12 @@ try {
773786
Write-Host "Deployment '$($deployment.DeploymentName)' has CorrelationId '$($deployment.CorrelationId)'"
774787
Write-Host "Successfully deployed template '$($templateFile.jsonFilePath)' to resource group '$($resourceGroup.ResourceGroupName)'"
775788

776-
$deploymentOutputs = SetDeploymentOutputs $serviceName $context $deployment $templateFile
789+
$deploymentEnvironmentVariables, $deploymentOutputs = SetDeploymentOutputs `
790+
-serviceName $serviceName `
791+
-azContext $context `
792+
-deployment $deployment `
793+
-templateFile $templateFile `
794+
-environmentVariables $EnvironmentVariables
777795

778796
$postDeploymentScript = $templateFile.originalFilePath | Split-Path | Join-Path -ChildPath "$ResourceType-resources-post.ps1"
779797
if (Test-Path $postDeploymentScript) {
@@ -793,7 +811,7 @@ try {
793811

794812
# Suppress output locally
795813
if ($CI) {
796-
return $EnvironmentVariables
814+
return $deploymentEnvironmentVariables
797815
}
798816

799817
<#

eng/common/TestResources/Remove-TestResources.ps1

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -147,14 +147,13 @@ if (!$ResourceGroupName) {
147147
exit 0
148148
}
149149
} else {
150-
if (!$BaseName) {
151-
$UserName = GetUserName
152-
$BaseName = GetBaseName $UserName $ServiceDirectory
153-
Log "BaseName was not set. Using default base name '$BaseName'"
154-
}
155-
156-
# Format the resource group name like in New-TestResources.ps1.
157-
$ResourceGroupName = "rg-$BaseName"
150+
$serviceName = GetServiceLeafDirectoryName $ServiceDirectory
151+
$BaseName, $ResourceGroupName = GetBaseAndResourceGroupNames `
152+
-baseNameDefault $BaseName `
153+
-resourceGroupNameDefault $ResourceGroupName `
154+
-user (GetUserName) `
155+
-serviceDirectoryName $serviceName `
156+
-CI $CI
158157
}
159158
}
160159

eng/common/TestResources/SubConfig-Helpers.ps1

Lines changed: 37 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,45 @@ function GetUserName() {
1616
return $UserName
1717
}
1818

19-
function GetBaseName([string]$user, [string]$serviceDirectoryName) {
19+
function GetBaseAndResourceGroupNames(
20+
[string]$baseNameDefault,
21+
[string]$resourceGroupNameDefault,
22+
[string]$user,
23+
[string]$serviceDirectoryName,
24+
[bool]$CI
25+
) {
26+
if ($CI) {
27+
$base = 't' + (New-Guid).ToString('n').Substring(0, 16)
28+
# Format the resource group name based on resource group naming recommendations and limitations.
29+
$generatedGroup = "rg-{0}-$base" -f ($serviceName -replace '[\.\\\/:]', '-').
30+
Substring(0, [Math]::Min($serviceDirectoryName.Length, 90 - $base.Length - 4)).
31+
Trim('-').
32+
ToLowerInvariant()
33+
$group = $resourceGroupNameDefault ? $resourceGroupNameDefault : $generatedGroup
34+
35+
Log "Generated resource base name '$base' and resource group name '$group' for CI build"
36+
37+
return $base, $group
38+
}
39+
40+
if ($baseNameDefault) {
41+
$base = $baseNameDefault.ToLowerInvariant()
42+
$group = $resourceGroupNameDefault ? $resourceGroupNameDefault : ("rg-$baseNameDefault".ToLowerInvariant())
43+
return $base, $group
44+
}
45+
2046
# Handle service directories in nested directories, e.g. `data/aztables`
2147
$serviceDirectorySafeName = $serviceDirectoryName -replace '[\./\\]', ''
22-
return "$user$serviceDirectorySafeName".ToLowerInvariant()
48+
# Seed off resource group name if set to avoid name conflicts with deployments where it is not set
49+
$seed = $resourceGroupNameDefault ? $resourceGroupNameDefault : "${user}${serviceDirectorySafeName}"
50+
$baseNameStream = [IO.MemoryStream]::new([Text.Encoding]::UTF8.GetBytes("$seed"))
51+
# Hash to keep resource names short enough to not break naming restrictions (e.g. keyvault name length)
52+
$base = 't' + (Get-FileHash -InputStream $baseNameStream -Algorithm SHA256).Hash.Substring(0, 16).ToLowerInvariant()
53+
$group = $resourceGroupNameDefault ? $resourceGroupNameDefault : "rg-${user}${serviceDirectorySafeName}".ToLowerInvariant();
54+
55+
Log "BaseName was not set. Generating resource group name '$group' and resource base name '$base'"
56+
57+
return $base, $group
2358
}
2459

2560
function ShouldMarkValueAsSecret([string]$serviceName, [string]$key, [string]$value, [array]$allowedValues = @())

eng/common/TestResources/Update-TestResources.ps1

Lines changed: 7 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -69,17 +69,13 @@ $exitActions = @({
6969
}
7070
})
7171

72-
# Make sure $ResourceGroupName is set.
73-
if (!$ResourceGroupName) {
74-
# Make sure $BaseName is set.
75-
if (!$BaseName) {
76-
$UserName = GetUserName
77-
$BaseName = GetBaseName $UserName $ServiceDirectory
78-
Log "BaseName was not set. Using default base name '$BaseName'"
79-
}
80-
81-
$ResourceGroupName = "rg-$BaseName"
82-
}
72+
$serviceName = GetServiceLeafDirectoryName $ServiceDirectory
73+
$BaseName, $ResourceGroupName = GetBaseAndResourceGroupNames `
74+
-baseNameDefault $BaseName `
75+
-resourceGroupNameDefault $ResourceGroupName `
76+
-user (GetUserName) `
77+
-serviceDirectoryName $serviceName `
78+
-CI $false
8379

8480
# This script is intended for interactive users. Make sure they are logged in or fail.
8581
$context = Get-AzContext

0 commit comments

Comments
 (0)