From 0ef0c4e53819174a1309c419de48dd93097312f3 Mon Sep 17 00:00:00 2001 From: Flor Elisa Chacon Ochoa Date: Tue, 27 Oct 2026 14:45:33 -0700 Subject: [PATCH] Add vcpkg initialization script and use it in pipeline --- azure-pipelines.yml | 16 +++------------- doc/Developing.md | 4 +++- templates/README.md | 30 +++++------------------------- templates/jobs-build.yml | 27 ++++----------------------- tools/Initialize-Vcpkg.ps1 | 32 ++++++++++++++++++++++++++++++++ 5 files changed, 47 insertions(+), 62 deletions(-) create mode 100644 tools/Initialize-Vcpkg.ps1 diff --git a/azure-pipelines.yml b/azure-pipelines.yml index 2702f6b6c7..e31dd66ffd 100644 --- a/azure-pipelines.yml +++ b/azure-pipelines.yml @@ -79,12 +79,10 @@ jobs: feedsToUse: 'config' nugetConfigPath: '$(nugetConfig)' - - task: CmdLine@2 - displayName: Enable Vcpkg Install + - task: PowerShell@2 + displayName: Initialize Vcpkg inputs: - script: | - $(VCPKG_INSTALLATION_ROOT)\vcpkg.exe integrate install - workingDirectory: '$(VCPKG_INSTALLATION_ROOT)' + filePath: 'tools\Initialize-Vcpkg.ps1' - task: VSBuild@1 displayName: Build Fuzzing Artifacts @@ -95,14 +93,6 @@ jobs: msbuildArgs: '/bl:$(artifactsDir)\msbuild.binlog' maximumCpuCount: true - - task: CopyFiles@2 - displayName: Copy vcpkg logs - inputs: - SourceFolder: $(VCPKG_INSTALLATION_ROOT)\buildtrees - Contents: '**\*.log' - TargetFolder: '$(artifactsDir)\vcpkgLogs' - condition: succeededOrFailed() - - task: CopyFiles@2 displayName: Copy Fuzzing Artifacts for Publishing inputs: diff --git a/doc/Developing.md b/doc/Developing.md index 1584ba052d..e94cbfc746 100644 --- a/doc/Developing.md +++ b/doc/Developing.md @@ -32,7 +32,9 @@ For naming, formatting, error handling, casts, `std::move()` usage, and resource - For VS Community: `winget configure .config/configuration.winget` - For VS Professional: `winget configure .config/configuration.vsProfessional.winget` - For VS Enterprise: `winget configure .config/configuration.vsEnterprise.winget` -3. Run `vcpkg integrate install` from the Developer Command Prompt / Developer PowerShell for VS. This is a one-time setup step until the configuration file in step 2 is updated to work with vcpkg setup. +3. From PowerShell at the repository root, run [`.\tools\Initialize-Vcpkg.ps1`](../tools/Initialize-Vcpkg.ps1) to enable MSBuild integration with Visual Studio's bundled vcpkg. + This replaces any existing vcpkg integration for the current user. + This is a one-time setup step until the configuration file in step 2 is updated to work with vcpkg setup. Open `winget-cli\src\AppInstallerCLI.sln` in Visual Studio and build. We currently only build using the solution; command-line methods of building a VS solution should work as well. diff --git a/templates/README.md b/templates/README.md index 5aa383446f..15c998a14f 100644 --- a/templates/README.md +++ b/templates/README.md @@ -53,12 +53,9 @@ Paths that belong to the agent or to the build output are deliberately **not** r they do not move with the subtree: - `$(Build.ArtifactStagingDirectory)`, `$(Pipeline.Workspace)` -- `$(Agent.TempDirectory)`, `$(VCPKG_INSTALLATION_ROOT)` +- `$(Agent.TempDirectory)` - `$(buildOutDir)`, `$(buildOutDirAnyCpu)`, `$(artifactsDir)`, `$(packageLayoutDir)` -`$(VCPKG_INSTALLATION_ROOT)` is the exception worth calling out: it is correctly *not* rooted, but a -consumer may not use the installation it points at. See `useAgentVcpkg` below. - Nested template references need no help. Azure Pipelines resolves a `- template:` reference inside a template file relative to *that file*, so the job templates find their siblings at any depth. Only the entry point has to know where the subtree lives. @@ -84,9 +81,10 @@ is neither a parameter nor a path in this directory. **Pipeline variables.** None. `jobs-build.yml` sets what it needs at job scope — `solution`, so it can be rooted, and `EnableDetectorVcpkg`, so Component Governance detects the vcpkg dependencies. -**A Windows agent** with Visual Studio 2022 and vcpkg, exposing `VCPKG_INSTALLATION_ROOT`. The -Microsoft-hosted `windows-2025` image qualifies. **The `Test` and `BuildPowerShellModule` jobs need -more than the `Build` job does — see "Agent requirements" below.** +**A Windows agent** with Visual Studio 2022 or newer and its vcpkg component installed. The `Build` job +runs [tools\Initialize-Vcpkg.ps1](../tools/Initialize-Vcpkg.ps1) to enable user-wide MSBuild integration +with Visual Studio's bundled vcpkg. +**The `Test` and `BuildPowerShellModule` jobs need more than the `Build` job does — see "Agent requirements" below.** **Outbound network access.** The test jobs reach several public endpoints, which is worth checking before wiring this up on a restricted network: @@ -194,24 +192,6 @@ does not even build. /p:UseProdCLSIDs=false ``` -## `useAgentVcpkg` - -Defaults to `true`, matching the Microsoft-hosted images, where `VCPKG_INSTALLATION_ROOT` points at -a real vcpkg installation that this pipeline integrates and builds the native dependencies with. - -Set it to `false` when the consuming repository supplies vcpkg some other way — for example through -an MSBuild SDK that restores the ports itself. `VCPKG_INSTALLATION_ROOT` may well still be defined in -that case, since the agent image sets it, but nothing builds there. Two steps then become -meaningless and are dropped together: - -- *Enable Vcpkg Install*, which integrates an installation the build does not use. -- *Copy vcpkg logs*, which reads `$(VCPKG_INSTALLATION_ROOT)\buildtrees` — a directory that will not - exist, failing the job after a successful build. - -Dropping the log collection loses no real diagnostics: `Build Solution` writes an MSBuild binary log -to `$(artifactsDir)\msbuild.binlog`, which is published with the rest of the build artifacts and -records the vcpkg invocation and its output. - ## `releaseTagJob` `jobs-build.yml` stamps a build version obtained from a separate job. That job is named by the diff --git a/templates/jobs-build.yml b/templates/jobs-build.yml index a24e8fc343..d0b630e04d 100644 --- a/templates/jobs-build.yml +++ b/templates/jobs-build.yml @@ -24,13 +24,6 @@ parameters: - name: additionalMSBuildArgs type: string default: '' -# Whether the agent's own vcpkg installation, at VCPKG_INSTALLATION_ROOT, is what builds the native -# dependencies. Set to false when a consuming repository supplies vcpkg by other means, such as an -# MSBuild SDK; the integrate step and the port log collection below are then both meaningless, -# because that variable points at an installation this build never uses. -- name: useAgentVcpkg - type: boolean - default: true # Agent pool for this job. Leave empty to inherit the pipeline's pool, which is what a pipeline # with a single suitable pool wants. See the "Agent requirements" section of README.md. - name: pool @@ -126,13 +119,10 @@ jobs: feedsToUse: 'config' nugetConfigPath: '$(nugetConfig)' - - ${{ if parameters.useAgentVcpkg }}: - - task: CmdLine@2 - displayName: Enable Vcpkg Install - inputs: - script: | - $(VCPKG_INSTALLATION_ROOT)\vcpkg.exe integrate install - workingDirectory: '$(VCPKG_INSTALLATION_ROOT)' + - task: PowerShell@2 + displayName: Initialize Vcpkg + inputs: + filePath: '${{ parameters.sourceRoot }}\tools\Initialize-Vcpkg.ps1' - ${{ if ne(parameters.releaseTagJob, '') }}: - task: PowerShell@2 @@ -180,15 +170,6 @@ jobs: ${{ parameters.additionalMSBuildArgs }}' maximumCpuCount: true - - ${{ if parameters.useAgentVcpkg }}: - - task: CopyFiles@2 - displayName: Copy vcpkg logs - inputs: - SourceFolder: $(VCPKG_INSTALLATION_ROOT)\buildtrees - Contents: '**\*.log' - TargetFolder: '$(artifactsDir)\vcpkgLogs' - condition: succeededOrFailed() - - task: CopyFiles@2 displayName: 'Copy specific build artifacts' inputs: diff --git a/tools/Initialize-Vcpkg.ps1 b/tools/Initialize-Vcpkg.ps1 new file mode 100644 index 0000000000..3f648cbaea --- /dev/null +++ b/tools/Initialize-Vcpkg.ps1 @@ -0,0 +1,32 @@ +<# +.SYNOPSIS + Enables user-wide MSBuild integration for Visual Studio's bundled vcpkg. +#> + +$ErrorActionPreference = 'Stop' + +$vswhere = "${env:ProgramFiles(x86)}\Microsoft Visual Studio\Installer\vswhere.exe" +if (-not (Test-Path -LiteralPath $vswhere -PathType Leaf)) +{ + throw "vswhere.exe not found at $vswhere." +} + +$vcpkg = & $vswhere -latest -products '*' ` + -requires Microsoft.VisualStudio.Component.Vcpkg ` + -find 'VC\vcpkg\vcpkg.exe' +if ($LASTEXITCODE -ne 0) +{ + throw "vswhere.exe failed with exit code $LASTEXITCODE." +} + +if (-not $vcpkg -or -not (Test-Path -LiteralPath $vcpkg -PathType Leaf)) +{ + throw 'No Visual Studio installation with vcpkg.exe found.' +} + +Write-Host "Running: `"$vcpkg`" integrate install" +& $vcpkg integrate install +if ($LASTEXITCODE -ne 0) +{ + throw "vcpkg integrate install failed with exit code $LASTEXITCODE." +}