From 3310d7fcd84a1e5610fb3fb93c8cf0308a460069 Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Thu, 8 Jun 2023 20:26:22 -0700 Subject: [PATCH 1/8] Support x86 and x64 MSI builds --- azure-pipelines.yml | 62 +++++++++++++++++++++++-- build_scripts/windows/Product.wxs | 53 +++++++++++++++++---- build_scripts/windows/azure-cli.sln | 6 +++ build_scripts/windows/azure-cli.wixproj | 36 ++++++++------ build_scripts/windows/scripts/build.cmd | 26 +++++++++-- 5 files changed, 154 insertions(+), 29 deletions(-) diff --git a/azure-pipelines.yml b/azure-pipelines.yml index 0df1e528ecf..02d357118e6 100644 --- a/azure-pipelines.yml +++ b/azure-pipelines.yml @@ -186,6 +186,12 @@ jobs: - job: BuildWindowsMSI displayName: Build Windows MSI + strategy: + matrix: + x86: + Platform: x86 + x64: + Platform: x64 dependsOn: ExtractMetadata condition: succeeded() @@ -200,6 +206,7 @@ jobs: - script: | + set /p ARCH=$(Platform) set /p CLI_VERSION=<$(System.ArtifactsDirectory)/metadata/version set @@ -209,12 +216,12 @@ jobs: - task: AzureArtifacts.manifest-generator-task.manifest-generator-task.ManifestGeneratorTask@0 displayName: 'SBOM' inputs: - BuildDropPath: 'build_scripts/windows/out/' + BuildDropPath: 'build_scripts/windows/out/$(Platform)' - task: PublishPipelineArtifact@0 displayName: 'Publish Artifact: MSI' inputs: - TargetPath: 'build_scripts/windows/out/' + TargetPath: 'build_scripts/windows/out/$(Platform)' ArtifactName: msi - job: TestWindowsMSI @@ -238,7 +245,54 @@ jobs: artifactName: msi - task: PowerShell@2 - displayName: Install and Load CLI + displayName: Install and Load x86 CLI + inputs: + targetType: inline + script: | + if (-NOT ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole] "Administrator")) { + # Start another Powershell process as Admin and execute this script again + $arguments = "& '" +$myinvocation.mycommand.definition + "'" + Start-Process powershell -Verb runAs -ArgumentList $arguments + # Stop if the PowerShell is not run as Admin + Break + } + # The following are executed by elevated PowerShell + az --version + + $InstallArgs = @( + "/i" + "`"$env:SYSTEM_ARTIFACTSDIRECTORY\msi\x86\Microsoft Azure CLI.msi`"" + "/q" + "/norestart" + "/l*v" + ".\install_logs.txt" + ) + $pre_installed_version=az version --query '\"azure-cli\"' -o tsv + $to_be_installed_version=Get-Content $(System.ArtifactsDirectory)/metadata/version + if ($pre_installed_version -eq $to_be_installed_version){ + # See https://docs.microsoft.com/windows/win32/msi/reinstallmode about options of REINSTALLMODE + $reinstall_option="REINSTALL=ALL REINSTALLMODE=emus" + $InstallArgs += $reinstall_option + } + Start-Process "msiexec.exe" -ArgumentList $InstallArgs -Wait -NoNewWindow + $install_time=Measure-Command {Start-Process "msiexec.exe" -ArgumentList $InstallArgs -Wait -NoNewWindow} | select -expand TotalSeconds + $installed_version=az version --query '\"azure-cli\"' -o tsv + if ($installed_version -ne $to_be_installed_version){ + echo "The MSI failed to install." + Exit 1 + } + echo 'Install time(seconds):' $install_time + az --version + # Test bundled pip with extension installation + az extension add -n rdbms-connect + az self-test + + Get-Content .\install_logs.txt + + - task: PowerShell@2 + + # Test install (upgrade of x86) of x64 MSI as well. + displayName: Install and Load x64 CLI inputs: targetType: inline script: | @@ -254,7 +308,7 @@ jobs: $InstallArgs = @( "/i" - "`"$env:SYSTEM_ARTIFACTSDIRECTORY\msi\Microsoft Azure CLI.msi`"" + "`"$env:SYSTEM_ARTIFACTSDIRECTORY\msi\x64\Microsoft Azure CLI.msi`"" "/q" "/norestart" "/l*v" diff --git a/build_scripts/windows/Product.wxs b/build_scripts/windows/Product.wxs index b8b7d8d6a8b..2b05f50c41e 100644 --- a/build_scripts/windows/Product.wxs +++ b/build_scripts/windows/Product.wxs @@ -8,18 +8,55 @@ + + + + + + + + + + + + + + + + + + + + + + + UpgradeCode="$(var.UpgradeCode)"> - + + + + + NOT WIX_DOWNGRADE_DETECTED + + + + + + + + + + + @@ -61,7 +98,7 @@ - + @@ -78,17 +115,17 @@ + Guid="$(var.RemoveCLIFolderGuid)"> + Guid="$(var.RemoveAzureCLIFolderGuid)"> + Guid="$(var.AzureCliSystemPathGuid)"> + Guid="$(var.AzureCliRegistryGuid)"> + Guid="$(var.AzureCliVersionGuid)"> - - - artifacts\wix\ - $(LocalWixRoot) - $(WixToolPath)Wix.targets - wixtasks.dll - artifacts\cli - -fv - Debug @@ -21,14 +12,33 @@ $(MSBuildExtensionsPath32)\Microsoft\WiX\v3.x\Wix.targets $(MSBuildExtensionsPath)\Microsoft\WiX\v3.x\Wix.targets + + + artifacts\$(Platform)\wix + $(LocalWixRoot) + $(WixToolPath)\Wix.targets + wixtasks.dll + artifacts\$(Platform)\cli + -fv + - out\$(Configuration)\ - out\obj\$(Configuration)\ + out\$(Platform)\$(Configuration)\ + out\obj\$(Platform)\$(Configuration)\ Debug;AzureCliSource=$(AzureCliSource) - out\ - out\obj\$(Configuration)\ + out\$(Platform)\ + out\obj\$(Platform)\$(Configuration)\ + AzureCliSource=$(AzureCliSource) + + + out\$(Platform)\$(Configuration)\ + out\obj\$(Platform)\$(Configuration)\ + Debug;AzureCliSource=$(AzureCliSource) + + + out\$(Platform)\ + out\obj\$(Platform)\$(Configuration)\ AzureCliSource=$(AzureCliSource) diff --git a/build_scripts/windows/scripts/build.cmd b/build_scripts/windows/scripts/build.cmd index 3944e96b925..e2f65b289b8 100644 --- a/build_scripts/windows/scripts/build.cmd +++ b/build_scripts/windows/scripts/build.cmd @@ -13,10 +13,22 @@ if "%CLI_VERSION%"=="" ( echo Please set the CLI_VERSION environment variable, e.g. 2.0.13 goto ERROR ) + +if "%ARCH%"=="" ( + set ARCH=x86 +) +if "%ARCH%"=="x86" ( + set PYTHON_ARCH=win32 +) else if "%ARCH%"=="x64" ( + set PYTHON_ARCH=amd64 +) else ( + echo Please set ARCH to "x86" or "x64" + goto ERROR +) set PYTHON_VERSION=3.10.10 set WIX_DOWNLOAD_URL="https://azurecliprod.blob.core.windows.net/msi/wix310-binaries-mirror.zip" -set PYTHON_DOWNLOAD_URL="https://www.python.org/ftp/python/%PYTHON_VERSION%/python-%PYTHON_VERSION%-embed-win32.zip" +set PYTHON_DOWNLOAD_URL="https://www.python.org/ftp/python/%PYTHON_VERSION%/python-%PYTHON_VERSION%-embed-%PYTHON_ARCH%.zip" REM https://pip.pypa.io/en/stable/installation/#get-pip-py set GET_PIP_DOWNLOAD_URL="https://bootstrap.pypa.io/get-pip.py" @@ -27,14 +39,17 @@ set OUTPUT_DIR=%~dp0..\out if exist %OUTPUT_DIR% rmdir /s /q %OUTPUT_DIR% mkdir %OUTPUT_DIR% -set ARTIFACTS_DIR=%~dp0..\artifacts +set ARTIFACTS_DIR=%~dp0..\artifacts\%ARCH% mkdir %ARTIFACTS_DIR% set TEMP_SCRATCH_FOLDER=%ARTIFACTS_DIR%\cli_scratch set BUILDING_DIR=%ARTIFACTS_DIR%\cli set WIX_DIR=%ARTIFACTS_DIR%\wix set PYTHON_DIR=%ARTIFACTS_DIR%\Python -set REPO_ROOT=%~dp0..\..\.. +REM Get the absolute directory since we pushd into different levels of subdirectories. +PUSHD %~dp0..\..\.. +SET REPO_ROOT=%CD% +POPD REM reset working folders if exist %BUILDING_DIR% rmdir /s /q %BUILDING_DIR% @@ -72,6 +87,9 @@ if not exist %WIX_DIR% ( popd ) +REM Use only downloaded python and ignore machine state +set PYTHONHOME=%PYTHON_DIR% + REM ensure Python is available if exist %PYTHON_DIR% ( echo Using existing Python at %PYTHON_DIR% @@ -181,7 +199,7 @@ popd if %errorlevel% neq 0 goto ERROR echo Building MSI... -msbuild /t:rebuild /p:Configuration=Release %REPO_ROOT%\build_scripts\windows\azure-cli.wixproj +msbuild /t:rebuild /p:Configuration=Release /p:Platform=%ARCH% %REPO_ROOT%\build_scripts\windows\azure-cli.wixproj if %errorlevel% neq 0 goto ERROR From cbff2cbc4f00ebc5e4c1a154077af2b0fb854e0b Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Mon, 12 Jun 2023 14:05:48 -0700 Subject: [PATCH 2/8] Fix spacing in pipeline YAML --- azure-pipelines.yml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/azure-pipelines.yml b/azure-pipelines.yml index 02d357118e6..72ffd2f31f6 100644 --- a/azure-pipelines.yml +++ b/azure-pipelines.yml @@ -289,8 +289,7 @@ jobs: Get-Content .\install_logs.txt - - task: PowerShell@2 - + - task: PowerShell@2 # Test install (upgrade of x86) of x64 MSI as well. displayName: Install and Load x64 CLI inputs: From 496e7d10b5ea1d384b864b00e328229d5ab124e8 Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Fri, 7 Jul 2023 00:32:39 -0700 Subject: [PATCH 3/8] Remove multi-platform build support Separate agents will build separate packages and publish them as needed to avoid regressions to existing pipeline. --- azure-pipelines.yml | 68 +++++-------------------- build_scripts/windows/azure-cli.wixproj | 20 ++++---- build_scripts/windows/scripts/build.cmd | 5 +- 3 files changed, 25 insertions(+), 68 deletions(-) diff --git a/azure-pipelines.yml b/azure-pipelines.yml index 72ffd2f31f6..923ce17138f 100644 --- a/azure-pipelines.yml +++ b/azure-pipelines.yml @@ -206,8 +206,8 @@ jobs: - script: | - set /p ARCH=$(Platform) - set /p CLI_VERSION=<$(System.ArtifactsDirectory)/metadata/version + set ARCH=$(Platform) + set CLI_VERSION=<$(System.ArtifactsDirectory)/metadata/version set build_scripts/windows/scripts/build.cmd @@ -216,16 +216,22 @@ jobs: - task: AzureArtifacts.manifest-generator-task.manifest-generator-task.ManifestGeneratorTask@0 displayName: 'SBOM' inputs: - BuildDropPath: 'build_scripts/windows/out/$(Platform)' + BuildDropPath: 'build_scripts/windows/out/' - task: PublishPipelineArtifact@0 displayName: 'Publish Artifact: MSI' inputs: - TargetPath: 'build_scripts/windows/out/$(Platform)' - ArtifactName: msi + TargetPath: 'build_scripts/windows/out/' + ArtifactName: msi-$(Platform) - job: TestWindowsMSI displayName: Test Windows MSI + strategy: + matrix: + x86: + Platform: x86 + x64: + Platform: x64 dependsOn: BuildWindowsMSI condition: and(succeeded(), in(variables['Build.Reason'], 'IndividualCI', 'BatchedCI', 'Manual', 'Schedule')) @@ -242,56 +248,10 @@ jobs: displayName: 'Download Build Artifacts' inputs: TargetPath: '$(Build.ArtifactStagingDirectory)/msi' - artifactName: msi - - - task: PowerShell@2 - displayName: Install and Load x86 CLI - inputs: - targetType: inline - script: | - if (-NOT ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole] "Administrator")) { - # Start another Powershell process as Admin and execute this script again - $arguments = "& '" +$myinvocation.mycommand.definition + "'" - Start-Process powershell -Verb runAs -ArgumentList $arguments - # Stop if the PowerShell is not run as Admin - Break - } - # The following are executed by elevated PowerShell - az --version - - $InstallArgs = @( - "/i" - "`"$env:SYSTEM_ARTIFACTSDIRECTORY\msi\x86\Microsoft Azure CLI.msi`"" - "/q" - "/norestart" - "/l*v" - ".\install_logs.txt" - ) - $pre_installed_version=az version --query '\"azure-cli\"' -o tsv - $to_be_installed_version=Get-Content $(System.ArtifactsDirectory)/metadata/version - if ($pre_installed_version -eq $to_be_installed_version){ - # See https://docs.microsoft.com/windows/win32/msi/reinstallmode about options of REINSTALLMODE - $reinstall_option="REINSTALL=ALL REINSTALLMODE=emus" - $InstallArgs += $reinstall_option - } - Start-Process "msiexec.exe" -ArgumentList $InstallArgs -Wait -NoNewWindow - $install_time=Measure-Command {Start-Process "msiexec.exe" -ArgumentList $InstallArgs -Wait -NoNewWindow} | select -expand TotalSeconds - $installed_version=az version --query '\"azure-cli\"' -o tsv - if ($installed_version -ne $to_be_installed_version){ - echo "The MSI failed to install." - Exit 1 - } - echo 'Install time(seconds):' $install_time - az --version - # Test bundled pip with extension installation - az extension add -n rdbms-connect - az self-test - - Get-Content .\install_logs.txt + artifactName: msi-$(Platform) - task: PowerShell@2 - # Test install (upgrade of x86) of x64 MSI as well. - displayName: Install and Load x64 CLI + displayName: Install and Load CLI inputs: targetType: inline script: | @@ -307,7 +267,7 @@ jobs: $InstallArgs = @( "/i" - "`"$env:SYSTEM_ARTIFACTSDIRECTORY\msi\x64\Microsoft Azure CLI.msi`"" + "`"$env:SYSTEM_ARTIFACTSDIRECTORY\msi\Microsoft Azure CLI.msi`"" "/q" "/norestart" "/l*v" diff --git a/build_scripts/windows/azure-cli.wixproj b/build_scripts/windows/azure-cli.wixproj index 3da211995d8..fea2075d330 100644 --- a/build_scripts/windows/azure-cli.wixproj +++ b/build_scripts/windows/azure-cli.wixproj @@ -14,31 +14,31 @@ - artifacts\$(Platform)\wix + artifacts\wix $(LocalWixRoot) $(WixToolPath)\Wix.targets wixtasks.dll - artifacts\$(Platform)\cli + artifacts\cli -fv - out\$(Platform)\$(Configuration)\ - out\obj\$(Platform)\$(Configuration)\ + out\$(Configuration)\ + out\obj\$(Configuration)\ Debug;AzureCliSource=$(AzureCliSource) - out\$(Platform)\ - out\obj\$(Platform)\$(Configuration)\ + out\ + out\obj\$(Configuration)\ AzureCliSource=$(AzureCliSource) - out\$(Platform)\$(Configuration)\ - out\obj\$(Platform)\$(Configuration)\ + out\$(Configuration)\ + out\obj\$(Configuration)\ Debug;AzureCliSource=$(AzureCliSource) - out\$(Platform)\ - out\obj\$(Platform)\$(Configuration)\ + out\ + out\obj\$(Configuration)\ AzureCliSource=$(AzureCliSource) diff --git a/build_scripts/windows/scripts/build.cmd b/build_scripts/windows/scripts/build.cmd index e2f65b289b8..94414ed694b 100644 --- a/build_scripts/windows/scripts/build.cmd +++ b/build_scripts/windows/scripts/build.cmd @@ -39,7 +39,7 @@ set OUTPUT_DIR=%~dp0..\out if exist %OUTPUT_DIR% rmdir /s /q %OUTPUT_DIR% mkdir %OUTPUT_DIR% -set ARTIFACTS_DIR=%~dp0..\artifacts\%ARCH% +set ARTIFACTS_DIR=%~dp0..\artifacts mkdir %ARTIFACTS_DIR% set TEMP_SCRATCH_FOLDER=%ARTIFACTS_DIR%\cli_scratch set BUILDING_DIR=%ARTIFACTS_DIR%\cli @@ -87,9 +87,6 @@ if not exist %WIX_DIR% ( popd ) -REM Use only downloaded python and ignore machine state -set PYTHONHOME=%PYTHON_DIR% - REM ensure Python is available if exist %PYTHON_DIR% ( echo Using existing Python at %PYTHON_DIR% From 78e26e630b463956b97791e05b1c66631afe8d95 Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Fri, 7 Jul 2023 01:06:03 -0700 Subject: [PATCH 4/8] Fix ICE61 --- build_scripts/windows/Product.wxs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/build_scripts/windows/Product.wxs b/build_scripts/windows/Product.wxs index 2b05f50c41e..1da688ce437 100644 --- a/build_scripts/windows/Product.wxs +++ b/build_scripts/windows/Product.wxs @@ -53,8 +53,8 @@ - - + + @@ -91,7 +91,7 @@ - NOT Installed AND NOT WIX_UPGRADE_DETECTED + NOT Installed AND NOT WIX_UPGRADE_DETECTED AND NOT WIX_X86_UPGRADE_DETECTED From 36ddbc04347651d7c4e6adbb5c2aa5807396147f Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Fri, 7 Jul 2023 01:09:33 -0700 Subject: [PATCH 5/8] Add /p back to set for expression support --- azure-pipelines.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/azure-pipelines.yml b/azure-pipelines.yml index 923ce17138f..54147edb1f3 100644 --- a/azure-pipelines.yml +++ b/azure-pipelines.yml @@ -207,7 +207,7 @@ jobs: - script: | set ARCH=$(Platform) - set CLI_VERSION=<$(System.ArtifactsDirectory)/metadata/version + set /p CLI_VERSION=<$(System.ArtifactsDirectory)/metadata/version set build_scripts/windows/scripts/build.cmd From efe327bbdcdc9cf33eb847a5d1b067a4c3ae5cd9 Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Mon, 17 Jul 2023 22:18:31 -0700 Subject: [PATCH 6/8] Resolve PR feedback --- build_scripts/windows/Product.wxs | 4 +++- build_scripts/windows/azure-cli.wixproj | 6 +++--- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/build_scripts/windows/Product.wxs b/build_scripts/windows/Product.wxs index 1da688ce437..d1af0a19b46 100644 --- a/build_scripts/windows/Product.wxs +++ b/build_scripts/windows/Product.wxs @@ -45,7 +45,6 @@ - NOT WIX_DOWNGRADE_DETECTED @@ -56,6 +55,9 @@ + NOT (WIX_DOWNGRADE_DETECTED OR WIX_X86_DOWNGRADE_DETECTED) + + NOT WIX_DOWNGRADE_DETECTED diff --git a/build_scripts/windows/azure-cli.wixproj b/build_scripts/windows/azure-cli.wixproj index fea2075d330..e0497237fbd 100644 --- a/build_scripts/windows/azure-cli.wixproj +++ b/build_scripts/windows/azure-cli.wixproj @@ -15,9 +15,9 @@ artifacts\wix - $(LocalWixRoot) + $(MSBuildThisFileDirectory)$(LocalWixRoot) $(WixToolPath)\Wix.targets - wixtasks.dll + $(WixToolPath)\wixtasks.dll artifacts\cli -fv @@ -65,4 +65,4 @@ - \ No newline at end of file + From 16ed951223594e99c15b2f973e4094129e430890 Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Wed, 19 Jul 2023 00:26:24 -0700 Subject: [PATCH 7/8] Upgrade x86 from 64-bit version --- build_scripts/windows/Product.wxs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/build_scripts/windows/Product.wxs b/build_scripts/windows/Product.wxs index d1af0a19b46..eb12cb875bd 100644 --- a/build_scripts/windows/Product.wxs +++ b/build_scripts/windows/Product.wxs @@ -42,7 +42,7 @@ InstallScope="perMachine" /> - + @@ -52,7 +52,7 @@ - + NOT (WIX_DOWNGRADE_DETECTED OR WIX_X86_DOWNGRADE_DETECTED) @@ -93,7 +93,7 @@ - NOT Installed AND NOT WIX_UPGRADE_DETECTED AND NOT WIX_X86_UPGRADE_DETECTED + NOT Installed AND NOT WIX_UPGRADE_DETECTED From c2e85ec1c37939fee29998ffdf14871bc88adc67 Mon Sep 17 00:00:00 2001 From: Heath Stewart Date: Wed, 19 Jul 2023 10:36:33 -0700 Subject: [PATCH 8/8] Add architecture to ProductName --- build_scripts/windows/Product.wxs | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/build_scripts/windows/Product.wxs b/build_scripts/windows/Product.wxs index eb12cb875bd..2db951f4a06 100644 --- a/build_scripts/windows/Product.wxs +++ b/build_scripts/windows/Product.wxs @@ -7,6 +7,7 @@ + @@ -16,6 +17,7 @@ + @@ -24,14 +26,15 @@ - + + - - + + - NOT (WIX_DOWNGRADE_DETECTED OR WIX_X86_DOWNGRADE_DETECTED) + NOT (WIX_DOWNGRADE_DETECTED OR WIX_X86_DOWNGRADE_DETECTED) - NOT WIX_DOWNGRADE_DETECTED + NOT WIX_DOWNGRADE_DETECTED