From a2e0390537f7ba8f190c97b5592aaf64f7731a47 Mon Sep 17 00:00:00 2001 From: Jared Holgate Date: Fri, 15 Mar 2024 18:07:36 +0000 Subject: [PATCH] Bug fixing and refactoring for e2e tests (#107) # Pull Request ## Description This PR is part of the major refactoring work to de-couple the bootstrap and support bicep automation. The fixes and refactoring in this branch were designed to make the e2e tests pass successfully. You can see the successful test run for this branch here: - PR: https://github.com/Azure/accelerator-bootstrap-modules/pull/1 - Test Run: https://github.com/Azure/accelerator-bootstrap-modules/actions/runs/8288999772/job/22684596007?pr=1 ## License By submitting this pull request, I confirm that my contribution is made under the terms of the projects associated license. --- actions_bootstrap_for_e2e_tests.ps1 | 37 ++++++ src/ALZ.build.ps1 | 3 + .../Convert-HCLVariablesToUserInputConfig.ps1 | 2 + ...onvert-InterfaceInputToUserInputConfig.ps1 | 0 .../{ => Config-Helpers}/Get-ALZConfig.ps1 | 2 +- .../Request-ALZEnvironmentConfig.ps1 | 0 .../Request-ConfigurationValue.ps1 | 0 .../Request-SpecialInput.ps1 | 14 ++- .../Write-ConfigurationCache.ps1 | 0 .../{ => Config-Helpers}/Write-TfvarsFile.ps1 | 0 .../Get-BootstrapAndStarterConfig.ps1 | 84 ++++++++++++++ .../Get-ExistingLocalRelease.ps1 | 0 .../Invoke-FullUpgrade.ps1 | 0 .../Invoke-Terraform.ps1 | 0 .../Invoke-Upgrade.ps1 | 0 .../New-Bootstrap.ps1 | 14 ++- .../New-FolderStructure.ps1 | 2 +- .../New-ModuleSetup.ps1 | 37 ++++++ src/ALZ/Private/Get-StarterConfig.ps1 | 0 .../Build-ALZDeploymentEnvFile.ps1 | 0 .../Copy-ALZParametersFile.ps1 | 0 .../Edit-ALZConfigurationFilesInPlace.ps1 | 0 .../Format-TokenizedConfigurationString.ps1 | 0 .../New-ALZDirectoryEnvironment.ps1 | 0 .../New-ALZEnvironmentBicep.ps1 | 12 +- .../Set-ComputedConfiguration.ps1 | 0 .../Legacy-Bicep/Test-ALZGitRepository.ps1 | 37 ++++++ .../{ => Shared}/Get-GithubRelease.ps1 | 2 +- .../{ => Shared}/Get-OsArchitecture.ps1 | 0 .../{ => Shared}/Test-Utility-Functions.ps1 | 0 .../{ => Shared}/Write-InformationColored.ps1 | 0 src/ALZ/Private/Test-ALZGitRepository.ps1 | 25 ---- .../Private/{ => Tools}/Get-HCLParserTool.ps1 | 0 .../Private/{ => Tools}/Get-TerraformTool.ps1 | 0 src/ALZ/Public/New-ALZEnvironment.ps1 | 108 +++++++----------- .../Unit/Public/New-ALZEnvironment.Tests.ps1 | 36 ++++-- 36 files changed, 301 insertions(+), 114 deletions(-) create mode 100644 actions_bootstrap_for_e2e_tests.ps1 rename src/ALZ/Private/{ => Config-Helpers}/Convert-HCLVariablesToUserInputConfig.ps1 (92%) rename src/ALZ/Private/{ => Config-Helpers}/Convert-InterfaceInputToUserInputConfig.ps1 (100%) rename src/ALZ/Private/{ => Config-Helpers}/Get-ALZConfig.ps1 (96%) rename src/ALZ/Private/{ => Config-Helpers}/Request-ALZEnvironmentConfig.ps1 (100%) rename src/ALZ/Private/{ => Config-Helpers}/Request-ConfigurationValue.ps1 (100%) rename src/ALZ/Private/{ => Config-Helpers}/Request-SpecialInput.ps1 (80%) rename src/ALZ/Private/{ => Config-Helpers}/Write-ConfigurationCache.ps1 (100%) rename src/ALZ/Private/{ => Config-Helpers}/Write-TfvarsFile.ps1 (100%) create mode 100644 src/ALZ/Private/Deploy-Accelerator-Helpers/Get-BootstrapAndStarterConfig.ps1 rename src/ALZ/Private/{ => Deploy-Accelerator-Helpers}/Get-ExistingLocalRelease.ps1 (100%) rename src/ALZ/Private/{ => Deploy-Accelerator-Helpers}/Invoke-FullUpgrade.ps1 (100%) rename src/ALZ/Private/{ => Deploy-Accelerator-Helpers}/Invoke-Terraform.ps1 (100%) rename src/ALZ/Private/{ => Deploy-Accelerator-Helpers}/Invoke-Upgrade.ps1 (100%) rename src/ALZ/Private/{ => Deploy-Accelerator-Helpers}/New-Bootstrap.ps1 (94%) rename src/ALZ/Private/{ => Deploy-Accelerator-Helpers}/New-FolderStructure.ps1 (93%) create mode 100644 src/ALZ/Private/Deploy-Accelerator-Helpers/New-ModuleSetup.ps1 delete mode 100644 src/ALZ/Private/Get-StarterConfig.ps1 rename src/ALZ/Private/{ => Legacy-Bicep}/Build-ALZDeploymentEnvFile.ps1 (100%) rename src/ALZ/Private/{ => Legacy-Bicep}/Copy-ALZParametersFile.ps1 (100%) rename src/ALZ/Private/{ => Legacy-Bicep}/Edit-ALZConfigurationFilesInPlace.ps1 (100%) rename src/ALZ/Private/{ => Legacy-Bicep}/Format-TokenizedConfigurationString.ps1 (100%) rename src/ALZ/Private/{ => Legacy-Bicep}/New-ALZDirectoryEnvironment.ps1 (100%) rename src/ALZ/Private/{ => Legacy-Bicep}/New-ALZEnvironmentBicep.ps1 (84%) rename src/ALZ/Private/{ => Legacy-Bicep}/Set-ComputedConfiguration.ps1 (100%) create mode 100644 src/ALZ/Private/Legacy-Bicep/Test-ALZGitRepository.ps1 rename src/ALZ/Private/{ => Shared}/Get-GithubRelease.ps1 (98%) rename src/ALZ/Private/{ => Shared}/Get-OsArchitecture.ps1 (100%) rename src/ALZ/Private/{ => Shared}/Test-Utility-Functions.ps1 (100%) rename src/ALZ/Private/{ => Shared}/Write-InformationColored.ps1 (100%) delete mode 100644 src/ALZ/Private/Test-ALZGitRepository.ps1 rename src/ALZ/Private/{ => Tools}/Get-HCLParserTool.ps1 (100%) rename src/ALZ/Private/{ => Tools}/Get-TerraformTool.ps1 (100%) diff --git a/actions_bootstrap_for_e2e_tests.ps1 b/actions_bootstrap_for_e2e_tests.ps1 new file mode 100644 index 0000000..98943ef --- /dev/null +++ b/actions_bootstrap_for_e2e_tests.ps1 @@ -0,0 +1,37 @@ +# Bootstrap dependencies + +# https://docs.microsoft.com/powershell/module/packagemanagement/get-packageprovider +Get-PackageProvider -Name Nuget -ForceBootstrap | Out-Null + +# https://docs.microsoft.com/powershell/module/powershellget/set-psrepository +Set-PSRepository -Name PSGallery -InstallationPolicy Trusted + +# List of PowerShell Modules required for the build +$modulesToInstall = [System.Collections.ArrayList]::new() +# https://github.com/nightroman/Invoke-Build +$null = $modulesToInstall.Add(([PSCustomObject]@{ + ModuleName = 'InvokeBuild' + ModuleVersion = '5.10.2' + })) + +'Installing PowerShell Modules' +foreach ($module in $modulesToInstall) { + $installSplat = @{ + Name = $module.ModuleName + RequiredVersion = $module.ModuleVersion + Repository = 'PSGallery' + SkipPublisherCheck = $true + Force = $true + ErrorAction = 'Stop' + } + try { + Install-Module @installSplat + Import-Module -Name $module.ModuleName -ErrorAction Stop + ' - Successfully installed {0}' -f $module.ModuleName + } catch { + $message = 'Failed to install {0}' -f $module.ModuleName + " - $message" + throw + } +} + diff --git a/src/ALZ.build.ps1 b/src/ALZ.build.ps1 index b11c67d..3b0af45 100644 --- a/src/ALZ.build.ps1 +++ b/src/ALZ.build.ps1 @@ -64,6 +64,9 @@ Add-BuildTask HelpLocal Clean, ImportModuleManifest, CreateHelpStart #Full build sans integration tests Add-BuildTask BuildNoIntegration -Jobs $str2 +#Build and Install Only +Add-BuildTask BuildAndInstallOnly Clean, ImportModuleManifest, Build, Archive, Install + # Pre-build variables to be used by other portions of the script Enter-Build { $script:ModuleName = (Split-Path -Path $BuildFile -Leaf).Split('.')[0] diff --git a/src/ALZ/Private/Convert-HCLVariablesToUserInputConfig.ps1 b/src/ALZ/Private/Config-Helpers/Convert-HCLVariablesToUserInputConfig.ps1 similarity index 92% rename from src/ALZ/Private/Convert-HCLVariablesToUserInputConfig.ps1 rename to src/ALZ/Private/Config-Helpers/Convert-HCLVariablesToUserInputConfig.ps1 index 44477ae..c5dc6d4 100644 --- a/src/ALZ/Private/Convert-HCLVariablesToUserInputConfig.ps1 +++ b/src/ALZ/Private/Config-Helpers/Convert-HCLVariablesToUserInputConfig.ps1 @@ -55,6 +55,7 @@ function Convert-HCLVariablesToUserInputConfig { $inputType = "UserInput" if($allComputedInputs) { $inputType = "ComputedInput" + Write-Verbose "Name: $($variable.Name), Has Validation: $hasValidation, Order: $order, ValidationType: $validationType, Description: $description, InputType: $inputType" } $sensitive = $false @@ -90,6 +91,7 @@ function Convert-HCLVariablesToUserInputConfig { } if($hasValidation) { + Write-Verbose "Validation: $hasValidation - $validationType" $validator = $validators.PSObject.Properties[$validationType].Value $description = "$description ($($validator.Description))" if($validator.Type -eq "AllowedValues"){ diff --git a/src/ALZ/Private/Convert-InterfaceInputToUserInputConfig.ps1 b/src/ALZ/Private/Config-Helpers/Convert-InterfaceInputToUserInputConfig.ps1 similarity index 100% rename from src/ALZ/Private/Convert-InterfaceInputToUserInputConfig.ps1 rename to src/ALZ/Private/Config-Helpers/Convert-InterfaceInputToUserInputConfig.ps1 diff --git a/src/ALZ/Private/Get-ALZConfig.ps1 b/src/ALZ/Private/Config-Helpers/Get-ALZConfig.ps1 similarity index 96% rename from src/ALZ/Private/Get-ALZConfig.ps1 rename to src/ALZ/Private/Config-Helpers/Get-ALZConfig.ps1 index 785122e..8844c86 100644 --- a/src/ALZ/Private/Get-ALZConfig.ps1 +++ b/src/ALZ/Private/Config-Helpers/Get-ALZConfig.ps1 @@ -39,6 +39,6 @@ function Get-ALZConfig { throw "The config file must be a json or yaml/yml file" } - Write-Verbose "Config file loaded from $configFilePath with $($config.PSObject.Properties.Count) properties." + Write-Verbose "Config file loaded from $configFilePath with $($config.PSObject.Properties.Name.Count) properties." return $config } \ No newline at end of file diff --git a/src/ALZ/Private/Request-ALZEnvironmentConfig.ps1 b/src/ALZ/Private/Config-Helpers/Request-ALZEnvironmentConfig.ps1 similarity index 100% rename from src/ALZ/Private/Request-ALZEnvironmentConfig.ps1 rename to src/ALZ/Private/Config-Helpers/Request-ALZEnvironmentConfig.ps1 diff --git a/src/ALZ/Private/Request-ConfigurationValue.ps1 b/src/ALZ/Private/Config-Helpers/Request-ConfigurationValue.ps1 similarity index 100% rename from src/ALZ/Private/Request-ConfigurationValue.ps1 rename to src/ALZ/Private/Config-Helpers/Request-ConfigurationValue.ps1 diff --git a/src/ALZ/Private/Request-SpecialInput.ps1 b/src/ALZ/Private/Config-Helpers/Request-SpecialInput.ps1 similarity index 80% rename from src/ALZ/Private/Request-SpecialInput.ps1 rename to src/ALZ/Private/Config-Helpers/Request-SpecialInput.ps1 index 5db8eb3..1dbe4da 100644 --- a/src/ALZ/Private/Request-SpecialInput.ps1 +++ b/src/ALZ/Private/Config-Helpers/Request-SpecialInput.ps1 @@ -71,10 +71,18 @@ function Request-SpecialInput { Write-InformationColored "Please select the bootstrap module you would like to use, you can enter one of the following keys:" -ForegroundColor Yellow -InformationAction Continue $bootstrapOptions = @() - foreach ($bootstrapModule in $bootstrapModules.PsObject.Properties) { - Write-InformationColored "- $($bootstrapModule.Name) ($($bootstrapModule.Value.description))" -ForegroundColor Yellow -InformationAction Continue - $bootstrapOptions += $bootstrapModule.Name + if($bootstrapModules.PsObject.Properties.Name.Count -eq 0) { + $bootstrapOptions += "azuredevops" + Write-InformationColored "- azuredevops" -ForegroundColor Yellow -InformationAction Continue + $bootstrapOptions += "github" + Write-InformationColored "- github" -ForegroundColor Yellow -InformationAction Continue + } else { + foreach ($bootstrapModule in $bootstrapModules.PsObject.Properties) { + Write-InformationColored "- $($bootstrapModule.Name) ($($bootstrapModule.Value.description))" -ForegroundColor Yellow -InformationAction Continue + $bootstrapOptions += $bootstrapModule.Name + } } + Write-InformationColored ": " -ForegroundColor Yellow -NoNewline -InformationAction Continue $result = Read-Host diff --git a/src/ALZ/Private/Write-ConfigurationCache.ps1 b/src/ALZ/Private/Config-Helpers/Write-ConfigurationCache.ps1 similarity index 100% rename from src/ALZ/Private/Write-ConfigurationCache.ps1 rename to src/ALZ/Private/Config-Helpers/Write-ConfigurationCache.ps1 diff --git a/src/ALZ/Private/Write-TfvarsFile.ps1 b/src/ALZ/Private/Config-Helpers/Write-TfvarsFile.ps1 similarity index 100% rename from src/ALZ/Private/Write-TfvarsFile.ps1 rename to src/ALZ/Private/Config-Helpers/Write-TfvarsFile.ps1 diff --git a/src/ALZ/Private/Deploy-Accelerator-Helpers/Get-BootstrapAndStarterConfig.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/Get-BootstrapAndStarterConfig.ps1 new file mode 100644 index 0000000..a837572 --- /dev/null +++ b/src/ALZ/Private/Deploy-Accelerator-Helpers/Get-BootstrapAndStarterConfig.ps1 @@ -0,0 +1,84 @@ + +function Get-BootstrapAndStarterConfig { + [CmdletBinding(SupportsShouldProcess = $true)] + param( + [Parameter(Mandatory = $false)] + [string]$iac, + [Parameter(Mandatory = $false)] + [string]$bootstrap, + [Parameter(Mandatory = $false)] + [string]$bootstrapPath, + [Parameter(Mandatory = $false)] + [string]$bootstrapConfigPath, + [Parameter(Mandatory = $false)] + [PSCustomObject]$userInputOverrides + ) + + if ($PSCmdlet.ShouldProcess("Get Configuration for Bootstrap and Starter", "modify")) { + $hasStarterModule = $false + $starterModuleUrl = "" + $starterModuleSourceFolder = "" + $starterReleaseTag = "" + $starterPipelineFolder = "" + + $bootstrapDetails = $null + $validationConfig = $null + $inputConfig = $null + + # Get the bootstap configuration + $bootstrapConfigFullPath = Join-Path $bootstrapPath $bootstrapConfigPath + Write-Verbose "Bootstrap config path $bootstrapConfigFullPath" + $bootstrapConfig = Get-ALZConfig -configFilePath $bootstrapConfigFullPath + $validationConfig = $bootstrapConfig.validators + + # Get the available bootstrap modules + $bootstrapModules = $bootstrapConfig.bootstrap_modules + + # Request the bootstrap type if not already specified + if($bootstrap -eq "") { + $bootstrap = Request-SpecialInput -type "bootstrap" -bootstrapModules $bootstrapModules -userInputOverrides $userInputOverrides + } + + # Get the bootstrap details and validate it exists (use alias for legacy values) + $bootstrapDetails = $bootstrapModules.PsObject.Properties | Where-Object { $_.Name -eq $bootstrap -or $bootstrap -in $_.Value.aliases } + if($null -eq $bootstrapDetails) { + Write-InformationColored "The bootstrap type '$bootstrap' that you have selected does not exist. Please try again with a valid bootstrap type..." -ForegroundColor Red -InformationAction Continue + throw + } + + # Get the starter modules for the selected bootstrap if it has any + $bootstrapStarterModule = $bootstrapDetails.Value.PSObject.Properties | Where-Object { $_.Name -eq "starter_modules" } + + if($null -ne $bootstrapStarterModule) { + # If the bootstrap has starter modules, get the details and url + $hasStarterModule = $true + $starterModules = $bootstrapConfig.PSObject.Properties | Where-Object { $_.Name -eq "starter_modules" } + $starterModuleType = $bootstrapStarterModule.Value + $starterModuleDetails = $starterModules.Value.PSObject.Properties | Where-Object { $_.Name -eq $starterModuleType } + if($null -eq $starterModuleDetails) { + Write-InformationColored "The starter modules '$($starterModuleType)' for the bootstrap type '$bootstrap' that you have selected does not exist. This could be an issue with your custom configuration, please check and try again..." -ForegroundColor Red -InformationAction Continue + throw + } + + $starterModuleUrl = $starterModuleDetails.Value.$iac.url + $starterModuleSourceFolder = $starterModuleDetails.Value.$iac.module_path + $starterPipelineFolder = $starterModuleDetails.Value.$iac.pipeline_folder + } + + # Get the bootstrap interface user input config + $inputConfigFilePath = Join-Path -Path $bootstrapPath -ChildPath $bootstrapDetails.Value.interface_config_file + Write-Verbose "Interface config path $inputConfigFilePath" + $inputConfig = Get-ALZConfig -configFilePath $inputConfigFilePath + + return @{ + bootstrapDetails = $bootstrapDetails + hasStarterModule = $hasStarterModule + starterModuleUrl = $starterModuleUrl + starterModuleSourceFolder = $starterModuleSourceFolder + starterReleaseTag = $starterReleaseTag + starterPipelineFolder = $starterPipelineFolder + validationConfig = $validationConfig + inputConfig = $inputConfig + } + } +} diff --git a/src/ALZ/Private/Get-ExistingLocalRelease.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/Get-ExistingLocalRelease.ps1 similarity index 100% rename from src/ALZ/Private/Get-ExistingLocalRelease.ps1 rename to src/ALZ/Private/Deploy-Accelerator-Helpers/Get-ExistingLocalRelease.ps1 diff --git a/src/ALZ/Private/Invoke-FullUpgrade.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/Invoke-FullUpgrade.ps1 similarity index 100% rename from src/ALZ/Private/Invoke-FullUpgrade.ps1 rename to src/ALZ/Private/Deploy-Accelerator-Helpers/Invoke-FullUpgrade.ps1 diff --git a/src/ALZ/Private/Invoke-Terraform.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/Invoke-Terraform.ps1 similarity index 100% rename from src/ALZ/Private/Invoke-Terraform.ps1 rename to src/ALZ/Private/Deploy-Accelerator-Helpers/Invoke-Terraform.ps1 diff --git a/src/ALZ/Private/Invoke-Upgrade.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/Invoke-Upgrade.ps1 similarity index 100% rename from src/ALZ/Private/Invoke-Upgrade.ps1 rename to src/ALZ/Private/Deploy-Accelerator-Helpers/Invoke-Upgrade.ps1 diff --git a/src/ALZ/Private/New-Bootstrap.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/New-Bootstrap.ps1 similarity index 94% rename from src/ALZ/Private/New-Bootstrap.ps1 rename to src/ALZ/Private/Deploy-Accelerator-Helpers/New-Bootstrap.ps1 index 117aa15..7bdd568 100644 --- a/src/ALZ/Private/New-Bootstrap.ps1 +++ b/src/ALZ/Private/Deploy-Accelerator-Helpers/New-Bootstrap.ps1 @@ -43,6 +43,9 @@ function New-Bootstrap { if ($PSCmdlet.ShouldProcess("ALZ-Terraform module configuration", "modify")) { + $bootstrapPath = Join-Path $bootstrapTargetPath $bootstrapRelease + $starterPath = Join-Path $starterTargetPath $starterRelease + # Setup tools $hclParserToolPath = Get-HCLParserTool -alzEnvironmentDestination $bootstrapPath -toolVersion "v0.6.0" @@ -57,8 +60,6 @@ function New-Bootstrap { $starterCachePath = Join-Path -Path $starterPath -ChildPath $starterCacheFileName $starterCachedConfig = Get-ALZConfig -configFilePath $starterCachePath - $bootstrapPath = Join-Path $bootstrapTargetPath $bootstrapRelease - $starterPath = Join-Path $starterTargetPath $starterRelease $bootstrapModulePath = Join-Path -Path $bootstrapPath -ChildPath $bootstrapDetails.Value.location Write-Verbose "Bootstrap Module Path: $bootstrapModulePath" @@ -82,8 +83,11 @@ function New-Bootstrap { if($hasStarter) { $starter = Request-SpecialInput -type "starter" -starterPath $starterPath -userInputOverrides $userInputOverrides - $starterModulePath = Join-Path -Path $starterPath -ChildPath $starter - $pipelineModulePath = Join-Path -Path $starterPath -ChildPath $starterPipelineFolder + $starterModulePath = Resolve-Path (Join-Path -Path $starterPath -ChildPath $starter) + $pipelineModulePath = Resolve-Path (Join-Path -Path $starterPath -ChildPath $starterPipelineFolder) + + Write-Verbose "Starter Module Path: $starterModulePath" + Write-Verbose "Pipeline Module Path: $pipelineModulePath" } # Getting the configuration for the interface user input @@ -109,7 +113,7 @@ function New-Bootstrap { if($hasStarter) { $targetVariableFilePath = Join-Path -Path $starterModulePath -ChildPath "variables.tf" - $starterParameters = Convert-HCLVariablesToUserInputConfig -targetVariableFile $targetVariableFilePath -hclParserToolPath $hclParserToolPath -validators $bootstrapConfig.validators + $starterParameters = Convert-HCLVariablesToUserInputConfig -targetVariableFile $targetVariableFilePath -hclParserToolPath $hclParserToolPath -validators $validationConfig } # Filter interface inputs if not in bootstrap or starter diff --git a/src/ALZ/Private/New-FolderStructure.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/New-FolderStructure.ps1 similarity index 93% rename from src/ALZ/Private/New-FolderStructure.ps1 rename to src/ALZ/Private/Deploy-Accelerator-Helpers/New-FolderStructure.ps1 index 45c357e..05b86e2 100644 --- a/src/ALZ/Private/New-FolderStructure.ps1 +++ b/src/ALZ/Private/Deploy-Accelerator-Helpers/New-FolderStructure.ps1 @@ -39,7 +39,7 @@ function New-FolderStructure { } else { Write-InformationColored "Copying files from $overrideSourceDirectoryPath to $path" -ForegroundColor Green -InformationAction Continue New-Item -Path $path -ItemType "Directory" - Copy-Item -Path "$overrideSourceDirectoryPath/$sourceFolder/*" -Destination "$path" -Recurse | Out-String | Write-Verbose + Copy-Item -Path "$overrideSourceDirectoryPath/$sourceFolder/*" -Destination "$path" -Recurse -Force | Out-String | Write-Verbose } } else { diff --git a/src/ALZ/Private/Deploy-Accelerator-Helpers/New-ModuleSetup.ps1 b/src/ALZ/Private/Deploy-Accelerator-Helpers/New-ModuleSetup.ps1 new file mode 100644 index 0000000..68e98f9 --- /dev/null +++ b/src/ALZ/Private/Deploy-Accelerator-Helpers/New-ModuleSetup.ps1 @@ -0,0 +1,37 @@ + +function New-ModuleSetup { + [CmdletBinding(SupportsShouldProcess = $true)] + param( + [Parameter(Mandatory = $false)] + [string]$targetDirectory, + [Parameter(Mandatory = $false)] + [string]$targetFolder, + [Parameter(Mandatory = $false)] + [string]$sourceFolder, + [Parameter(Mandatory = $false)] + [string]$url, + [Parameter(Mandatory = $false)] + [string]$release, + [Parameter(Mandatory = $false)] + [string]$moduleOverrideFolderPath, + [Parameter(Mandatory = $false)] + [bool]$skipInternetChecks + ) + + if ($PSCmdlet.ShouldProcess("Check and get module", "modify")) { + $versionAndPath = $null + + if($skipInternetChecks) { + $versionAndPath = Get-ExistingLocalRelease -targetDirectory $targetDirectory -targetFolder $targetFolder + } else { + $versionAndPath = New-FolderStructure ` + -targetDirectory $targetDirectory ` + -url $url ` + -release $release ` + -targetFolder $targetFolder ` + -sourceFolder $sourceFolder ` + -overrideSourceDirectoryPath $moduleOverrideFolderPath + } + return $versionAndPath + } +} diff --git a/src/ALZ/Private/Get-StarterConfig.ps1 b/src/ALZ/Private/Get-StarterConfig.ps1 deleted file mode 100644 index e69de29..0000000 diff --git a/src/ALZ/Private/Build-ALZDeploymentEnvFile.ps1 b/src/ALZ/Private/Legacy-Bicep/Build-ALZDeploymentEnvFile.ps1 similarity index 100% rename from src/ALZ/Private/Build-ALZDeploymentEnvFile.ps1 rename to src/ALZ/Private/Legacy-Bicep/Build-ALZDeploymentEnvFile.ps1 diff --git a/src/ALZ/Private/Copy-ALZParametersFile.ps1 b/src/ALZ/Private/Legacy-Bicep/Copy-ALZParametersFile.ps1 similarity index 100% rename from src/ALZ/Private/Copy-ALZParametersFile.ps1 rename to src/ALZ/Private/Legacy-Bicep/Copy-ALZParametersFile.ps1 diff --git a/src/ALZ/Private/Edit-ALZConfigurationFilesInPlace.ps1 b/src/ALZ/Private/Legacy-Bicep/Edit-ALZConfigurationFilesInPlace.ps1 similarity index 100% rename from src/ALZ/Private/Edit-ALZConfigurationFilesInPlace.ps1 rename to src/ALZ/Private/Legacy-Bicep/Edit-ALZConfigurationFilesInPlace.ps1 diff --git a/src/ALZ/Private/Format-TokenizedConfigurationString.ps1 b/src/ALZ/Private/Legacy-Bicep/Format-TokenizedConfigurationString.ps1 similarity index 100% rename from src/ALZ/Private/Format-TokenizedConfigurationString.ps1 rename to src/ALZ/Private/Legacy-Bicep/Format-TokenizedConfigurationString.ps1 diff --git a/src/ALZ/Private/New-ALZDirectoryEnvironment.ps1 b/src/ALZ/Private/Legacy-Bicep/New-ALZDirectoryEnvironment.ps1 similarity index 100% rename from src/ALZ/Private/New-ALZDirectoryEnvironment.ps1 rename to src/ALZ/Private/Legacy-Bicep/New-ALZDirectoryEnvironment.ps1 diff --git a/src/ALZ/Private/New-ALZEnvironmentBicep.ps1 b/src/ALZ/Private/Legacy-Bicep/New-ALZEnvironmentBicep.ps1 similarity index 84% rename from src/ALZ/Private/New-ALZEnvironmentBicep.ps1 rename to src/ALZ/Private/Legacy-Bicep/New-ALZEnvironmentBicep.ps1 index b0e63d8..a258cb0 100644 --- a/src/ALZ/Private/New-ALZEnvironmentBicep.ps1 +++ b/src/ALZ/Private/Legacy-Bicep/New-ALZEnvironmentBicep.ps1 @@ -10,12 +10,18 @@ function New-ALZEnvironmentBicep { [Parameter(Mandatory = $false)] [string] $upstreamReleaseFolderPath, + [Parameter(Mandatory = $false)] + [PSCustomObject] $userInputOverrides = $null, + [Parameter(Mandatory = $false)] [ValidateSet("github", "azuredevops")] [string] $vcs, [Parameter(Mandatory = $false)] - [switch] $local + [switch] $local, + + [Parameter(Mandatory = $false)] + [switch] $autoApprove ) if ($PSCmdlet.ShouldProcess("ALZ-Bicep module configuration", "modify")) { @@ -31,14 +37,14 @@ function New-ALZEnvironmentBicep { Copy-ALZParametersFile -alzEnvironmentDestination $targetDirectory -upstreamReleaseDirectory $upstreamReleaseFolderPath -configFiles $bicepConfig.config_files | Out-String | Write-Verbose Copy-ALZParametersFile -alzEnvironmentDestination $targetDirectory -upstreamReleaseDirectory $upstreamReleaseFolderPath -configFiles $bicepConfig.cicd.$vcs | Out-String | Write-Verbose - $configuration = Request-ALZEnvironmentConfig -configurationParameters $bicepConfig.parameters + $configuration = Request-ALZEnvironmentConfig -configurationParameters $bicepConfig.parameters -userInputOverrides $userInputOverrides -autoApprove:$autoApprove.IsPresent Set-ComputedConfiguration -configuration $configuration | Out-String | Write-Verbose Edit-ALZConfigurationFilesInPlace -alzEnvironmentDestination $targetDirectory -configuration $configuration | Out-String | Write-Verbose Build-ALZDeploymentEnvFile -configuration $configuration -Destination $targetDirectory -version $upstreamReleaseVersion | Out-String | Write-Verbose if($local) { - $isGitRepo = Test-ALZGitRepository -alzEnvironmentDestination $targetDirectory + $isGitRepo = Test-ALZGitRepository -alzEnvironmentDestination $targetDirectory -autoApprove:$autoApprove.IsPresent if (-not $isGitRepo) { Write-InformationColored "The directory $targetDirectory is not a git repository. Please make sure it is a git repo after initialization." -ForegroundColor Red -InformationAction Continue } diff --git a/src/ALZ/Private/Set-ComputedConfiguration.ps1 b/src/ALZ/Private/Legacy-Bicep/Set-ComputedConfiguration.ps1 similarity index 100% rename from src/ALZ/Private/Set-ComputedConfiguration.ps1 rename to src/ALZ/Private/Legacy-Bicep/Set-ComputedConfiguration.ps1 diff --git a/src/ALZ/Private/Legacy-Bicep/Test-ALZGitRepository.ps1 b/src/ALZ/Private/Legacy-Bicep/Test-ALZGitRepository.ps1 new file mode 100644 index 0000000..ecee5ad --- /dev/null +++ b/src/ALZ/Private/Legacy-Bicep/Test-ALZGitRepository.ps1 @@ -0,0 +1,37 @@ +function Test-ALZGitRepository { + [CmdletBinding(SupportsShouldProcess = $true)] + param ( + [Parameter(Mandatory = $true)] + [Alias("Output")] + [Alias("OutputDirectory")] + [Alias("O")] + [string] $alzEnvironmentDestination, + [Parameter(Mandatory = $false)] + [switch] $autoApprove + ) + $gitDirectory = Join-Path $alzEnvironmentDestination ".git" + if (Test-Path $gitDirectory) { + Write-Verbose "The directory $alzEnvironmentDestination is already a git repository." + return $true + } + + $runGitInit = $true + $gitBranch = "main" + + if(!$autoApprove) { + $gitInit = Read-Host "Initialize the directory $alzEnvironmentDestination as a git repository? (y/n)" + if ($gitInit -ieq "y") { + $runGitInit = $true + $gitBranch = Read-Host "Enter the default branch name. (Hit enter to skip and use 'main')" + if ($gitBranch -eq "") { + $gitBranch = "main" + } + } + } + + if($runGitInit -and $PSCmdlet.ShouldProcess("gitrepository", "initialize")) { + git init -b $gitBranch $alzEnvironmentDestination + } + + return $runGitInit +} diff --git a/src/ALZ/Private/Get-GithubRelease.ps1 b/src/ALZ/Private/Shared/Get-GithubRelease.ps1 similarity index 98% rename from src/ALZ/Private/Get-GithubRelease.ps1 rename to src/ALZ/Private/Shared/Get-GithubRelease.ps1 index 82ee144..ef46a76 100644 --- a/src/ALZ/Private/Get-GithubRelease.ps1 +++ b/src/ALZ/Private/Shared/Get-GithubRelease.ps1 @@ -124,7 +124,7 @@ function Get-GithubRelease { Write-Verbose "===> Copying all extracted contents into $targetVersionPath." - Copy-Item -Path "$($extractedSubFolder.FullName)/$moduleSourceFolder/*" -Destination "$targetVersionPath" -Recurse | Out-String | Write-Verbose + Copy-Item -Path "$($extractedSubFolder.FullName)/$moduleSourceFolder/*" -Destination "$targetVersionPath" -Recurse -Force | Out-String | Write-Verbose Remove-Item -Path "$targetVersionPath/tmp" -Force -Recurse Write-InformationColored "The directory for $targetVersionPath has been created and populated." -ForegroundColor Green -InformationAction Continue diff --git a/src/ALZ/Private/Get-OsArchitecture.ps1 b/src/ALZ/Private/Shared/Get-OsArchitecture.ps1 similarity index 100% rename from src/ALZ/Private/Get-OsArchitecture.ps1 rename to src/ALZ/Private/Shared/Get-OsArchitecture.ps1 diff --git a/src/ALZ/Private/Test-Utility-Functions.ps1 b/src/ALZ/Private/Shared/Test-Utility-Functions.ps1 similarity index 100% rename from src/ALZ/Private/Test-Utility-Functions.ps1 rename to src/ALZ/Private/Shared/Test-Utility-Functions.ps1 diff --git a/src/ALZ/Private/Write-InformationColored.ps1 b/src/ALZ/Private/Shared/Write-InformationColored.ps1 similarity index 100% rename from src/ALZ/Private/Write-InformationColored.ps1 rename to src/ALZ/Private/Shared/Write-InformationColored.ps1 diff --git a/src/ALZ/Private/Test-ALZGitRepository.ps1 b/src/ALZ/Private/Test-ALZGitRepository.ps1 deleted file mode 100644 index 29ef051..0000000 --- a/src/ALZ/Private/Test-ALZGitRepository.ps1 +++ /dev/null @@ -1,25 +0,0 @@ -function Test-ALZGitRepository { - [CmdletBinding(SupportsShouldProcess = $true)] - param ( - [Parameter(Mandatory = $true)] - [Alias("Output")] - [Alias("OutputDirectory")] - [Alias("O")] - [string] $alzEnvironmentDestination - ) - $gitDirectory = Join-Path $alzEnvironmentDestination ".git" - if (Test-Path $gitDirectory) { - Write-Verbose "The directory $alzEnvironmentDestination is already a git repository." - return $true - } - $gitInit = Read-Host "Initialize the directory $alzEnvironmentDestination as a git repository? (y/n)" - if ($gitInit -ieq "y" -and $PSCmdlet.ShouldProcess("gitrepository", "initialize")) { - $gitBranch = Read-Host "Enter the default branch name. (Hit enter to skip and use 'main')" - if ($gitBranch -eq "") { - $gitBranch = "main" - } - git init -b $gitBranch $alzEnvironmentDestination - return $true - } - return $false -} diff --git a/src/ALZ/Private/Get-HCLParserTool.ps1 b/src/ALZ/Private/Tools/Get-HCLParserTool.ps1 similarity index 100% rename from src/ALZ/Private/Get-HCLParserTool.ps1 rename to src/ALZ/Private/Tools/Get-HCLParserTool.ps1 diff --git a/src/ALZ/Private/Get-TerraformTool.ps1 b/src/ALZ/Private/Tools/Get-TerraformTool.ps1 similarity index 100% rename from src/ALZ/Private/Get-TerraformTool.ps1 rename to src/ALZ/Private/Tools/Get-TerraformTool.ps1 diff --git a/src/ALZ/Public/New-ALZEnvironment.ps1 b/src/ALZ/Public/New-ALZEnvironment.ps1 index 241ea89..095dcdf 100644 --- a/src/ALZ/Public/New-ALZEnvironment.ps1 +++ b/src/ALZ/Public/New-ALZEnvironment.ps1 @@ -147,21 +147,17 @@ function New-ALZEnvironment { $bootstrapTargetFolder = "bootstrap" if(!$isLegacyBicep) { - $versionAndPath = $null - Write-InformationColored "Checking and Downloading the bootstrap module..." -ForegroundColor Green -NewLineBefore -InformationAction Continue - if($skipInternetChecks) { - $versionAndPath = Get-ExistingLocalRelease -targetDirectory $targetDirectory -targetFolder $bootstrapTargetFolder - } else { - $versionAndPath = New-FolderStructure ` - -targetDirectory $targetDirectory ` - -url $bootstrapModuleUrl ` - -release $bootstrapRelease ` - -targetFolder $bootstrapTargetFolder ` - -sourceFolder $bootstrapSourceFolder ` - -overrideSourceDirectoryPath $bootstrapModuleOverrideFolderPath - } + $versionAndPath = New-ModuleSetup ` + -targetDirectory $targetDirectory ` + -targetFolder $bootstrapTargetFolder ` + -sourceFolder $bootstrapSourceFolder ` + -url $bootstrapModuleUrl ` + -release $bootstrapRelease ` + -moduleOverrideFolderPath $bootstrapModuleOverrideFolderPath ` + -skipInternetChecks $skipInternetChecks + $bootstrapReleaseTag = $versionAndPath.releaseTag $bootstrapPath = $versionAndPath.path } @@ -189,49 +185,25 @@ function New-ALZEnvironment { $inputConfig = $null if(!$isLegacyBicep) { - # Get the bootstap configuration - $bootstrapConfigPath = Join-Path $bootstrapPath $bootstrapConfigPath - $bootstrapConfig = Get-ALZConfig -configFilePath $bootstrapConfigPath - $validationConfig = $bootstrapConfig.validators - - # Get the available bootstrap modules - $bootstrapModules = $bootstrapConfig.bootstrap_modules - - # Request the bootstrap type if not already specified + $bootstrapAndStarterConfig = Get-BootstrapAndStarterConfig ` + -iac $iac ` + -bootstrap $bootstrap ` + -bootstrapPath $bootstrapPath ` + -bootstrapConfigPath $bootstrapConfigPath ` + -userInputOverrides $userInputOverrides + + $bootstrapDetails = $bootstrapAndStarterConfig.bootstrapDetails + $hasStarterModule = $bootstrapAndStarterConfig.hasStarterModule + $starterModuleUrl = $bootstrapAndStarterConfig.starterModuleUrl + $starterModuleSourceFolder = $bootstrapAndStarterConfig.starterModuleSourceFolder + $starterReleaseTag = $bootstrapAndStarterConfig.starterReleaseTag + $starterPipelineFolder = $bootstrapAndStarterConfig.starterPipelineFolder + $validationConfig = $bootstrapAndStarterConfig.validationConfig + $inputConfig = $bootstrapAndStarterConfig.inputConfig + } else { if($bootstrap -eq "") { $bootstrap = Request-SpecialInput -type "bootstrap" -bootstrapModules $bootstrapModules -userInputOverrides $userInputOverrides } - - # Get the bootstrap details and validate it exists (use alias for legacy values) - $bootstrapDetails = $bootstrapModules.PsObject.Properties | Where-Object { $_.Name -eq $bootstrap -or $bootstrap -in $_.Value.aliases } - if($null -eq $bootstrapDetails) { - Write-InformationColored "The bootstrap type '$bootstrap' that you have selected does not exist. Please try again with a valid bootstrap type..." -ForegroundColor Red -InformationAction Continue - return - } - - # Get the starter modules for the selected bootstrap if it has any - $bootstrapStarterModule = $bootstrapDetails.Value.PSObject.Properties | Where-Object { $_.Name -eq "starter_modules" } - - if($null -ne $bootstrapStarterModule) { - # If the bootstrap has starter modules, get the details and url - $hasStarterModule = $true - $starterModules = $bootstrapConfig.PSObject.Properties | Where-Object { $_.Name -eq "starter_modules" } - $starterModuleType = $bootstrapStarterModule.Value - $starterModuleDetails = $starterModules.Value.PSObject.Properties | Where-Object { $_.Name -eq $starterModuleType } - if($null -eq $starterModuleDetails) { - Write-InformationColored "The starter modules '$($starterModuleType)' for the bootstrap type '$bootstrap' that you have selected does not exist. This could be an issue with your custom configuration, please check and try again..." -ForegroundColor Red -InformationAction Continue - return - } - - $starterModuleUrl = $starterModuleDetails.Value.$iac.url - $starterModuleSourceFolder = $starterModuleDetails.Value.$iac.module_path - $starterPipelineFolder = $starterModuleDetails.Value.$iac.pipeline_folder - } - - # Get the bootstrap interface user input config - $inputConfigFilePath = Join-Path -Path $bootstrapPath -ChildPath $bootstrapDetails.Value.interface_config_file - Write-Verbose "Interface config path $inputConfigFilePath" - $inputConfig = Get-ALZConfig -configFilePath $inputConfigFilePath } # Download the starter modules @@ -239,21 +211,16 @@ function New-ALZEnvironment { $starterPath = "" if(($hasStarterModule -or $isLegacyBicep)) { - $versionAndPath = $null - Write-InformationColored "Checking and Downloading the starter module..." -ForegroundColor Green -NewLineBefore -InformationAction Continue - if($skipInternetChecks) { - $versionAndPath = Get-ExistingLocalRelease -targetDirectory $targetDirectory -targetFolder $starterModuleTargetFolder - } else { - $versionAndPath = New-FolderStructure ` - -targetDirectory $targetDirectory ` - -url $starterModuleUrl ` - -release $starterRelease ` - -targetFolder $starterModuleTargetFolder ` - -sourceFolder $starterModuleSourceFolder ` - -overrideSourceDirectoryPath $starterModuleOverrideFolderPath - } + $versionAndPath = New-ModuleSetup ` + -targetDirectory $targetDirectory ` + -targetFolder $starterModuleTargetFolder ` + -sourceFolder $starterModuleSourceFolder ` + -url $starterModuleUrl ` + -release $starterRelease ` + -moduleOverrideFolderPath $starterModuleOverrideFolderPath ` + -skipInternetChecks $skipInternetChecks $starterReleaseTag = $versionAndPath.releaseTag $starterPath = $versionAndPath.path @@ -261,15 +228,22 @@ function New-ALZEnvironment { # Run the bicep parameter setup if the iac is Bicep if ($iac -eq "bicep") { + Write-Verbose "Starting the Bicep specific environment setup..." + $bootstrapLegacy = $bootstrap.ToLower().Replace("alz_", "") + Write-Verbose "Bootstrap legacy: $bootstrapLegacy" $targetPath = Join-Path $targetDirectory $starterFolder + Write-Verbose "Target path: $targetPath" + New-ALZEnvironmentBicep ` -targetDirectory $targetPath ` -upstreamReleaseVersion $starterReleaseTag ` -upstreamReleaseFolderPath $starterPath ` -vcs $bootstrapLegacy ` - -local:$isLegacyBicep + -local:$isLegacyBicep ` + -autoApprove:$autoApprove.IsPresent ` + -userInputOverrides $userInputOverrides } # Run the bootstrap diff --git a/src/Tests/Unit/Public/New-ALZEnvironment.Tests.ps1 b/src/Tests/Unit/Public/New-ALZEnvironment.Tests.ps1 index 499f49d..6c0c5df 100644 --- a/src/Tests/Unit/Public/New-ALZEnvironment.Tests.ps1 +++ b/src/Tests/Unit/Public/New-ALZEnvironment.Tests.ps1 @@ -117,24 +117,44 @@ InModuleScope 'ALZ' { Mock -CommandName Invoke-FullUpgrade -MockWith { } Mock -CommandName Get-TerraformTool -MockWith {} + + Mock -CommandName New-FolderStructure -MockWith {} + + Mock -CommandName New-ModuleSetup -MockWith { + @{ + "version" = "v0.0.1" + "path" = "./example/example" + } + } + + Mock -CommandName Get-BootstrapAndStarterConfig -MockWith { + @{ + "hasStarterModule" = $true + } + } + + Mock -CommandName New-Bootstrap -MockWith {} + + Mock -CommandName New-ALZEnvironmentBicep -MockWith {} } It 'should call the correct functions for bicep legacy module configuration' { New-ALZEnvironment -i "bicep" -c "github" - Assert-MockCalled -CommandName Get-GithubRelease -Exactly 1 - Assert-MockCalled -CommandName Edit-ALZConfigurationFilesInPlace -Exactly 1 + Assert-MockCalled -CommandName New-ALZEnvironmentBicep -Exactly 1 + Assert-MockCalled -CommandName New-ModuleSetup -Exactly 1 } It 'should call the correct functions for bicep modern module configuration' { - New-ALZEnvironment -i "bicep" -c "github" - #Assert-MockCalled -CommandName Get-GithubRelease -Exactly 2 - Assert-MockCalled -CommandName Edit-ALZConfigurationFilesInPlace -Exactly 1 + Deploy-Accelerator -i "bicep" -c "github" -bicepLegacyMode $false + Assert-MockCalled -CommandName Get-BootstrapAndStarterConfig -Exactly 1 + Assert-MockCalled -CommandName New-ModuleSetup -Exactly 2 } It 'should call the correct functions for terraform module configuration' { - New-ALZEnvironment -i "terraform" -c "github" - #Assert-MockCalled -CommandName Get-GithubRelease -Exactly 2 - #Assert-MockCalled -CommandName Invoke-Terraform -Exactly 1 + Deploy-Accelerator -i "terraform" -c "github" + Assert-MockCalled -CommandName Get-BootstrapAndStarterConfig -Exactly 1 + Assert-MockCalled -CommandName New-Bootstrap -Exactly 1 + Assert-MockCalled -CommandName New-ModuleSetup -Exactly 2 } } }