Merge remote-tracking branch 'libtemplate/microbuild' into libtemplateUpdate
This commit is contained in:
Коммит
aabe7798d2
|
@ -167,5 +167,14 @@ dotnet_diagnostic.SA1130.severity = silent
|
|||
# IDE1006: Naming Styles - StyleCop handles these for us
|
||||
dotnet_diagnostic.IDE1006.severity = none
|
||||
|
||||
dotnet_diagnostic.DOC100.severity = silent
|
||||
dotnet_diagnostic.DOC104.severity = warning
|
||||
dotnet_diagnostic.DOC105.severity = warning
|
||||
dotnet_diagnostic.DOC106.severity = warning
|
||||
dotnet_diagnostic.DOC107.severity = warning
|
||||
dotnet_diagnostic.DOC108.severity = warning
|
||||
dotnet_diagnostic.DOC200.severity = warning
|
||||
dotnet_diagnostic.DOC202.severity = warning
|
||||
|
||||
[*.sln]
|
||||
indent_style = tab
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
*.user
|
||||
*.userosscache
|
||||
*.sln.docstates
|
||||
*.lutconfig
|
||||
launchSettings.json
|
||||
|
||||
# User-specific files (MonoDevelop/Xamarin Studio)
|
||||
|
@ -139,6 +140,7 @@ _TeamCity*
|
|||
# Visual Studio code coverage results
|
||||
*.coverage
|
||||
*.coveragexml
|
||||
/coveragereport/
|
||||
|
||||
# NCrunch
|
||||
_NCrunch_*
|
||||
|
|
|
@ -7,5 +7,36 @@ FAQ](https://opensource.microsoft.com/codeofconduct/faq/) or
|
|||
contact [opencode@microsoft.com](mailto:opencode@microsoft.com)
|
||||
with any additional questions or comments.
|
||||
|
||||
We welcome 3rd party pull requests.
|
||||
For significant changes we strongly recommend opening an issue to start a design discussion first.
|
||||
## Best practices
|
||||
|
||||
* Use Windows PowerShell or [PowerShell Core][pwsh] (including on Linux/OSX) to run .ps1 scripts.
|
||||
Some scripts set environment variables to help you, but they are only retained if you use PowerShell as your shell.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
All dependencies can be installed by running the `init.ps1` script at the root of the repository
|
||||
using Windows PowerShell or [PowerShell Core][pwsh] (on any OS).
|
||||
Some dependencies installed by `init.ps1` may only be discoverable from the same command line environment the init script was run from due to environment variables, so be sure to launch Visual Studio or build the repo from that same environment.
|
||||
Alternatively, run `init.ps1 -InstallLocality Machine` (which may require elevation) in order to install dependencies at machine-wide locations so Visual Studio and builds work everywhere.
|
||||
|
||||
The only prerequisite for building, testing, and deploying from this repository
|
||||
is the [.NET SDK](https://get.dot.net/).
|
||||
You should install the version specified in `global.json` or a later version within
|
||||
the same major.minor.Bxx "hundreds" band.
|
||||
For example if 2.2.300 is specified, you may install 2.2.300, 2.2.301, or 2.2.310
|
||||
while the 2.2.400 version would not be considered compatible by .NET SDK.
|
||||
See [.NET Core Versioning](https://docs.microsoft.com/dotnet/core/versions/) for more information.
|
||||
|
||||
## Package restore
|
||||
|
||||
The easiest way to restore packages may be to run `init.ps1` which automatically authenticates
|
||||
to the feeds that packages for this repo come from, if any.
|
||||
`dotnet restore` or `nuget restore` also work but may require extra steps to authenticate to any applicable feeds.
|
||||
|
||||
## Building
|
||||
|
||||
This repository can be built on Windows, Linux, and OSX.
|
||||
|
||||
Building, testing, and packing this repository can be done by using the standard dotnet CLI commands (e.g. `dotnet build`, `dotnet test`, `dotnet pack`, etc.).
|
||||
|
||||
[pwsh]: https://docs.microsoft.com/powershell/scripting/install/installing-powershell?view=powershell-6
|
||||
|
|
|
@ -16,6 +16,9 @@
|
|||
<!-- https://github.com/dotnet/msbuild/blob/main/documentation/ProjectReference-Protocol.md#setplatform-negotiation -->
|
||||
<EnableDynamicPlatformResolution>true</EnableDynamicPlatformResolution>
|
||||
|
||||
<!-- Opt in till https://github.com/NuGet/Home/issues/9803 makes this the default. -->
|
||||
<RestoreUseStaticGraphEvaluation>true</RestoreUseStaticGraphEvaluation>
|
||||
|
||||
<!-- This entire repo has just one version.json file, so compute the version once and share with all projects in a large build. -->
|
||||
<GitVersionBaseDirectory>$(MSBuildThisFileDirectory)</GitVersionBaseDirectory>
|
||||
|
||||
|
@ -30,20 +33,8 @@
|
|||
<EmbedUntrackedSources>true</EmbedUntrackedSources>
|
||||
<IncludeSymbols Condition=" '$(DebugType)' != 'embedded' ">true</IncludeSymbols>
|
||||
<SymbolPackageFormat>snupkg</SymbolPackageFormat>
|
||||
|
||||
<MicroBuildVersion>2.0.68</MicroBuildVersion>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.VisualStudio.Internal.MicroBuild.VisualStudio" Version="$(MicroBuildVersion)" PrivateAssets="all" />
|
||||
<PackageReference Include="Microsoft.NETFramework.ReferenceAssemblies" Version="1.0.2" PrivateAssets="all" />
|
||||
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.1.1" PrivateAssets="all" />
|
||||
<PackageReference Include="Nerdbank.GitVersioning" Version="3.5.107" PrivateAssets="all" />
|
||||
<PackageReference Include="Nullable" Version="1.3.0" PrivateAssets="all" />
|
||||
<!-- Use the Unstable package ID so that update tools will help us keep it current even though it seems to be ever-unstable lately. -->
|
||||
<PackageReference Include="StyleCop.Analyzers.Unstable" Version="1.2.0.435" PrivateAssets="all" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Include="$(RepoRootPath)obj/NOTICE" Pack="true" PackagePath="" Visible="false" Condition=" Exists('$(RepoRootPath)obj/NOTICE') " />
|
||||
</ItemGroup>
|
||||
|
@ -79,7 +70,7 @@
|
|||
It's also not necessary to generate these assets.
|
||||
-->
|
||||
<PropertyGroup Condition="'$(IsWpfTempProject)' == 'true'">
|
||||
<_WpfTempProjectNuGetFilePathNoExt>$(RepoRootPath)obj\$(_TargetAssemblyProjectName)\$(_TargetAssemblyProjectName)$(MSBuildProjectExtension).nuget.g</_WpfTempProjectNuGetFilePathNoExt>
|
||||
<_WpfTempProjectNuGetFilePathNoExt>$(BaseIntermediateOutputPath)..\$(_TargetAssemblyProjectName)\$(_TargetAssemblyProjectName)$(MSBuildProjectExtension).nuget.g</_WpfTempProjectNuGetFilePathNoExt>
|
||||
|
||||
<EnableSourceLink>false</EnableSourceLink>
|
||||
<EmbedUntrackedSources>false</EmbedUntrackedSources>
|
||||
|
|
|
@ -0,0 +1,25 @@
|
|||
<Project>
|
||||
<!-- https://learn.microsoft.com/nuget/consume-packages/central-package-management -->
|
||||
<PropertyGroup>
|
||||
<ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
|
||||
|
||||
<MicroBuildVersion>2.0.87</MicroBuildVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="17.3.2" />
|
||||
<PackageVersion Include="Moq" Version="4.18.1" />
|
||||
<PackageVersion Include="xunit.runner.visualstudio" Version="2.4.5" />
|
||||
<PackageVersion Include="xunit" Version="2.4.2" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<GlobalPackageReference Include="CSharpIsNullAnalyzer" Version="0.1.329" />
|
||||
<GlobalPackageReference Include="DotNetAnalyzers.DocumentationAnalyzers" Version="1.0.0-beta.59" />
|
||||
<GlobalPackageReference Include="Nerdbank.GitVersioning" Version="3.5.119" />
|
||||
<GlobalPackageReference Include="Nullable" Version="1.3.1" />
|
||||
<GlobalPackageReference Include="StyleCop.Analyzers.Unstable" Version="1.2.0.435" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<GlobalPackageReference Include="Microsoft.SourceLink.GitHub" Version="1.1.1" />
|
||||
<GlobalPackageReference Include="Microsoft.VisualStudio.Internal.MicroBuild.VisualStudio" Version="$(MicroBuildVersion)" />
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -0,0 +1,41 @@
|
|||
<!-- BEGIN MICROSOFT SECURITY.MD V0.0.5 BLOCK -->
|
||||
|
||||
## Security
|
||||
|
||||
Microsoft takes the security of our software products and services seriously, which includes all source code repositories managed through our GitHub organizations, which include [Microsoft](https://github.com/Microsoft), [Azure](https://github.com/Azure), [DotNet](https://github.com/dotnet), [AspNet](https://github.com/aspnet), [Xamarin](https://github.com/xamarin), and [our GitHub organizations](https://opensource.microsoft.com/).
|
||||
|
||||
If you believe you have found a security vulnerability in any Microsoft-owned repository that meets [Microsoft's definition of a security vulnerability](https://docs.microsoft.com/previous-versions/tn-archive/cc751383(v=technet.10)), please report it to us as described below.
|
||||
|
||||
## Reporting Security Issues
|
||||
|
||||
**Please do not report security vulnerabilities through public GitHub issues.**
|
||||
|
||||
Instead, please report them to the Microsoft Security Response Center (MSRC) at [https://msrc.microsoft.com/create-report](https://msrc.microsoft.com/create-report).
|
||||
|
||||
If you prefer to submit without logging in, send email to [secure@microsoft.com](mailto:secure@microsoft.com). If possible, encrypt your message with our PGP key; please download it from the [Microsoft Security Response Center PGP Key page](https://www.microsoft.com/msrc/pgp-key-msrc).
|
||||
|
||||
You should receive a response within 24 hours. If for some reason you do not, please follow up via email to ensure we received your original message. Additional information can be found at [microsoft.com/msrc](https://www.microsoft.com/msrc).
|
||||
|
||||
Please include the requested information listed below (as much as you can provide) to help us better understand the nature and scope of the possible issue:
|
||||
|
||||
* Type of issue (e.g. buffer overflow, SQL injection, cross-site scripting, etc.)
|
||||
* Full paths of source file(s) related to the manifestation of the issue
|
||||
* The location of the affected source code (tag/branch/commit or direct URL)
|
||||
* Any special configuration required to reproduce the issue
|
||||
* Step-by-step instructions to reproduce the issue
|
||||
* Proof-of-concept or exploit code (if possible)
|
||||
* Impact of the issue, including how an attacker might exploit the issue
|
||||
|
||||
This information will help us triage your report more quickly.
|
||||
|
||||
If you are reporting for a bug bounty, more complete reports can contribute to a higher bounty award. Please visit our [Microsoft Bug Bounty Program](https://microsoft.com/msrc/bounty) page for more details about our active programs.
|
||||
|
||||
## Preferred Languages
|
||||
|
||||
We prefer all communications to be in English.
|
||||
|
||||
## Policy
|
||||
|
||||
Microsoft follows the principle of [Coordinated Vulnerability Disclosure](https://www.microsoft.com/msrc/cvd).
|
||||
|
||||
<!-- END MICROSOFT SECURITY.MD BLOCK -->
|
|
@ -11,21 +11,27 @@ trigger:
|
|||
- '*.md'
|
||||
- .vscode/
|
||||
- .github/
|
||||
- azure-pipelines/release.yml
|
||||
|
||||
parameters:
|
||||
- name: includeMacOS
|
||||
displayName: Build on macOS
|
||||
type: boolean
|
||||
default: false # macOS is often bogged down in Azure Pipelines
|
||||
- name: RunTests
|
||||
displayName: Run tests
|
||||
type: boolean
|
||||
default: true
|
||||
|
||||
variables:
|
||||
TreatWarningsAsErrors: true
|
||||
DOTNET_SKIP_FIRST_TIME_EXPERIENCE: true
|
||||
BuildConfiguration: Release
|
||||
codecov_token: 1c079a51-729f-4e18-9792-2a75f2e074e0
|
||||
NUGET_PACKAGES: $(Agent.TempDirectory)/.nuget/packages
|
||||
NUGET_PACKAGES: $(Agent.TempDirectory)/.nuget/packages/
|
||||
|
||||
jobs:
|
||||
- template: azure-pipelines/build.yml
|
||||
parameters:
|
||||
includeMacOS: ${{ parameters.includeMacOS }}
|
||||
RunTests: ${{ parameters.RunTests }}
|
||||
|
|
|
@ -0,0 +1,220 @@
|
|||
#Requires -PSEdition Core -Version 7
|
||||
<#
|
||||
.SYNOPSIS
|
||||
Submits a source archival request for this repo.
|
||||
.PARAMETER Requester
|
||||
The alias for the user requesting this backup.
|
||||
.PARAMETER ManagerAlias
|
||||
The alias of the manager that owns the repo.
|
||||
.PARAMETER TeamAlias
|
||||
The alias of the team that owns the repo.
|
||||
.PARAMETER BusinessGroupName
|
||||
A human-readable title for your team or business group.
|
||||
.PARAMETER ProductionType
|
||||
.PARAMETER ReleaseType
|
||||
The type of release being backed up.
|
||||
.PARAMETER ReleaseDate
|
||||
The date of the release of your software. Defaults to today.
|
||||
.PARAMETER OwnerAlias
|
||||
The alias of the owner.
|
||||
.PARAMETER OS
|
||||
.PARAMETER ProductLanguage
|
||||
One or more languages.
|
||||
.PARAMETER Notes
|
||||
Any notes to record with the backup.
|
||||
.PARAMETER FileCollection
|
||||
One or more collections to archive.
|
||||
.PARAMETER ProductName
|
||||
The name of the product. This will default to the repository name.
|
||||
.PARAMETER RepoUrl
|
||||
The URL to the repository. This will default to the repository containing this script.
|
||||
.PARAMETER BackupType
|
||||
The kind of backup to be performed.
|
||||
.PARAMETER ServerPath
|
||||
The UNC path to the server to be backed up (if applicable).
|
||||
.PARAMETER SourceCodeArchivalUri
|
||||
The URI to POST the source code archival request to.
|
||||
This value will typically come automatically by a variable group associated with your pipeline.
|
||||
You can also look it up at https://dpsrequestforms.azurewebsites.net/#/help -> SCA Request Help -> SCA API Help -> Description
|
||||
#>
|
||||
[CmdletBinding(SupportsShouldProcess = $true, PositionalBinding = $false)]
|
||||
param (
|
||||
[Parameter()]
|
||||
[string]$Requester,
|
||||
[Parameter(Mandatory = $true)]
|
||||
[string]$ManagerAlias,
|
||||
[Parameter(Mandatory = $true)]
|
||||
[string]$TeamAlias,
|
||||
[Parameter(Mandatory = $true)]
|
||||
[string]$BusinessGroupName,
|
||||
[Parameter()]
|
||||
[string]$ProductionType = 'Visual Studio',
|
||||
[Parameter()]
|
||||
[string]$ReleaseType = 'RTW',
|
||||
[Parameter()]
|
||||
[DateTime]$ReleaseDate = [DateTime]::Today,
|
||||
[Parameter()]
|
||||
[string]$OwnerAlias,
|
||||
[Parameter()]
|
||||
[ValidateSet('64-Bit Win', '32-Bit Win', 'Linux', 'Mac', '64-Bit ARM', '32-Bit ARM')]
|
||||
[string[]]$OS = @('64-Bit Win'),
|
||||
[Parameter(Mandatory = $true)]
|
||||
[ValidateSet('English', 'Chinese Simplified', 'Chinese Traditional', 'Czech', 'French', 'German', 'Italian', 'Japanese', 'Korean', 'Polish', 'Portuguese', 'Russian', 'Spanish', 'Turkish')]
|
||||
[string[]]$ProductLanguage,
|
||||
[Parameter()]
|
||||
[string]$Notes = '',
|
||||
[Parameter()]
|
||||
[ValidateSet('Binaries', 'Localization', 'Source Code')]
|
||||
[string[]]$FileCollection = @('Source Code'),
|
||||
[Parameter()]
|
||||
[string]$ProductName,
|
||||
[Parameter()]
|
||||
[Uri]$RepoUrl,
|
||||
[Parameter()]
|
||||
[ValidateSet('Server Path', 'Code Repo(Git URL/AzureDevOps)', 'Git', 'Azure Storage Account')]
|
||||
[string]$BackupType = 'Code Repo(Git URL/AzureDevOps)',
|
||||
[Parameter()]
|
||||
[string]$ServerPath = '',
|
||||
[Parameter()]
|
||||
[Uri]$SourceCodeArchivalUri = $env:SOURCECODEARCHIVALURI
|
||||
)
|
||||
|
||||
function Invoke-Git() {
|
||||
# Make sure we invoke git from within the repo.
|
||||
Push-Location $PSScriptRoot
|
||||
try {
|
||||
return (git $args)
|
||||
}
|
||||
finally {
|
||||
Pop-Location
|
||||
}
|
||||
}
|
||||
|
||||
if (!$ProductName) {
|
||||
if ($env:BUILD_REPOSITORY_NAME) {
|
||||
Write-Verbose 'Using $env:BUILD_REPOSITORY_NAME for ProductName.' # single quotes are intentional so user sees the name of env var.
|
||||
$ProductName = $env:BUILD_REPOSITORY_NAME
|
||||
}
|
||||
else {
|
||||
$originUrl = [Uri](Invoke-Git remote get-url origin)
|
||||
if ($originUrl) {
|
||||
$lastPathSegment = $originUrl.Segments[$originUrl.Segments.Length - 1]
|
||||
if ($lastPathSegment.EndsWith('.git')) {
|
||||
$lastPathSegment = $lastPathSegment.Substring(0, $lastPathSegment.Length - '.git'.Length)
|
||||
}
|
||||
Write-Verbose 'Using origin remote URL to derive ProductName.'
|
||||
$ProductName = $lastPathSegment
|
||||
}
|
||||
}
|
||||
|
||||
if (!$ProductName) {
|
||||
Write-Error "Unable to determine default value for -ProductName."
|
||||
}
|
||||
}
|
||||
|
||||
if (!$OwnerAlias) {
|
||||
if ($env:BUILD_REQUESTEDFOREMAIL) {
|
||||
Write-Verbose 'Using $env:BUILD_REQUESTEDFOREMAIL and slicing to just the alias for OwnerAlias.'
|
||||
$OwnerAlias = ($env:BUILD_REQUESTEDFOREMAIL -split '@')[0]
|
||||
}
|
||||
else {
|
||||
Write-Verbose 'Using $env:USERNAME for OwnerAlias.'
|
||||
$OwnerAlias = $env:USERNAME
|
||||
}
|
||||
if (!$OwnerAlias) {
|
||||
Write-Error "Unable to determine default value for -OwnerAlias."
|
||||
}
|
||||
}
|
||||
|
||||
if (!$Requester) {
|
||||
if ($env:BUILD_REQUESTEDFOREMAIL) {
|
||||
Write-Verbose 'Using $env:BUILD_REQUESTEDFOREMAIL and slicing to just the alias for Requester.'
|
||||
$Requester = ($env:BUILD_REQUESTEDFOREMAIL -split '@')[0]
|
||||
}
|
||||
else {
|
||||
Write-Verbose 'Using $env:USERNAME for Requester.'
|
||||
$Requester = $env:USERNAME
|
||||
}
|
||||
if (!$Requester) {
|
||||
Write-Error "Unable to determine default value for -Requester."
|
||||
}
|
||||
}
|
||||
|
||||
if (!$RepoUrl) {
|
||||
$RepoUrl = $env:BUILD_REPOSITORY_URI
|
||||
if (!$RepoUrl) {
|
||||
$originUrl = [Uri](Invoke-Git remote get-url origin)
|
||||
if ($originUrl) {
|
||||
Write-Verbose 'Using git origin remote url for GitURL.'
|
||||
$RepoUrl = $originUrl
|
||||
}
|
||||
|
||||
if (!$RepoUrl) {
|
||||
Write-Error "Unable to determine default value for -RepoUrl."
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Push-Location $PSScriptRoot
|
||||
$versionsObj = & (& "$PSScriptRoot/Get-nbgv.ps1") get-version -f json | ConvertFrom-Json
|
||||
Pop-Location
|
||||
|
||||
$ReleaseDateString = $ReleaseDate.ToShortDateString()
|
||||
$Version = $versionsObj.Version
|
||||
|
||||
$BackupSize = Get-ChildItem $PSScriptRoot\..\.git -Recurse -File | Measure-Object -Property Length -Sum
|
||||
$DataSizeMB = [int]($BackupSize.Sum / 1mb)
|
||||
$FileCount = $BackupSize.Count
|
||||
|
||||
$Request = @{
|
||||
"Requester" = $Requester
|
||||
"Manager" = $ManagerAlias
|
||||
"TeamAlias" = $TeamAlias
|
||||
"AdditionalContacts" = $AdditionalContacts
|
||||
"BusinessGroupName" = $BusinessGroupName
|
||||
"ProductName" = $ProductName
|
||||
"Version" = $Version
|
||||
"ProductionType" = $ProductionType
|
||||
"ReleaseType" = $ReleaseType
|
||||
"ReleaseDateString" = $ReleaseDateString
|
||||
"OS" = [string]::Join(',', $OS)
|
||||
"ProductLanguage" = [string]::Join(',', $ProductLanguage)
|
||||
"FileCollection" = [string]::Join(',', $FileCollection)
|
||||
"OwnerAlias" = $OwnerAlias
|
||||
"Notes" = $Notes.Trim()
|
||||
"CustomerProvidedDataSizeMB" = $DataSizeMB
|
||||
"CustomerProvidedFileCount" = $FileCount
|
||||
"BackupType" = $BackupType
|
||||
"ServerPath" = $ServerPath
|
||||
"AzureStorageAccount" = $AzureStorageAccount
|
||||
"AzureStorageContainer" = $AzureStorageContainer
|
||||
"GitURL" = $RepoUrl
|
||||
}
|
||||
|
||||
$RequestJson = ConvertTo-Json $Request
|
||||
Write-Host "SCA request:`n$RequestJson"
|
||||
|
||||
if ($PSCmdlet.ShouldProcess('source archival request', 'post')) {
|
||||
if (!$SourceCodeArchivalUri) {
|
||||
Write-Error "Unable to post request without -SourceCodeArchivalUri parameter."
|
||||
exit 1
|
||||
}
|
||||
|
||||
[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
|
||||
|
||||
$Response = Invoke-WebRequest -Uri $SourceCodeArchivalUri -Method POST -Body $RequestJson -ContentType "application/json" -UseBasicParsing -SkipHttpErrorCheck
|
||||
Write-Host "Status Code : " -NoNewline
|
||||
$responseContent = ConvertFrom-Json ($Response.Content)
|
||||
if ($Response.StatusCode -eq 200) {
|
||||
Write-Host $Response.StatusCode -ForegroundColor Green
|
||||
Write-Host "Ticket ID : " -NoNewline
|
||||
Write-Host $responseContent
|
||||
}
|
||||
else {
|
||||
$responseContent = ConvertFrom-Json $Response.Content
|
||||
Write-Host $Response.StatusCode -ForegroundColor Red
|
||||
Write-Host "Message : $($responseContent.message)"
|
||||
}
|
||||
} elseif ($SourceCodeArchivalUri) {
|
||||
Write-Host "Would have posted to $SourceCodeArchivalUri"
|
||||
}
|
|
@ -8,36 +8,35 @@
|
|||
.PARAMETER OutputPath
|
||||
The path of the output PDB to write.
|
||||
#>
|
||||
#Function Convert-PortableToWindowsPDB() {
|
||||
Param(
|
||||
[Parameter(Mandatory=$true,Position=0)]
|
||||
[string]$DllPath,
|
||||
[Parameter()]
|
||||
[string]$PdbPath,
|
||||
[Parameter(Mandatory=$true,Position=1)]
|
||||
[string]$OutputPath
|
||||
)
|
||||
[CmdletBinding()]
|
||||
Param(
|
||||
[Parameter(Mandatory=$true,Position=0)]
|
||||
[string]$DllPath,
|
||||
[Parameter()]
|
||||
[string]$PdbPath,
|
||||
[Parameter(Mandatory=$true,Position=1)]
|
||||
[string]$OutputPath
|
||||
)
|
||||
|
||||
if ($IsMacOS -or $IsLinux) {
|
||||
Write-Error "This script only works on Windows"
|
||||
return
|
||||
}
|
||||
if ($IsMacOS -or $IsLinux) {
|
||||
Write-Error "This script only works on Windows"
|
||||
return
|
||||
}
|
||||
|
||||
$version = '1.1.0-beta2-21101-01'
|
||||
$baseDir = "$PSScriptRoot/../obj/tools"
|
||||
$pdb2pdbpath = "$baseDir/Microsoft.DiaSymReader.Pdb2Pdb.$version/tools/Pdb2Pdb.exe"
|
||||
if (-not (Test-Path $pdb2pdbpath)) {
|
||||
if (-not (Test-Path $baseDir)) { New-Item -Type Directory -Path $baseDir | Out-Null }
|
||||
$baseDir = (Resolve-Path $baseDir).Path # Normalize it
|
||||
Write-Verbose "& (& $PSScriptRoot/Get-NuGetTool.ps1) install Microsoft.DiaSymReader.Pdb2Pdb -version $version -PackageSaveMode nuspec -OutputDirectory $baseDir -Source https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json | Out-Null"
|
||||
& (& $PSScriptRoot/Get-NuGetTool.ps1) install Microsoft.DiaSymReader.Pdb2Pdb -version $version -PackageSaveMode nuspec -OutputDirectory $baseDir -Source https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json | Out-Null
|
||||
}
|
||||
$version = '1.1.0-beta2-21101-01'
|
||||
$baseDir = "$PSScriptRoot/../obj/tools"
|
||||
$pdb2pdbpath = "$baseDir/Microsoft.DiaSymReader.Pdb2Pdb.$version/tools/Pdb2Pdb.exe"
|
||||
if (-not (Test-Path $pdb2pdbpath)) {
|
||||
if (-not (Test-Path $baseDir)) { New-Item -Type Directory -Path $baseDir | Out-Null }
|
||||
$baseDir = (Resolve-Path $baseDir).Path # Normalize it
|
||||
Write-Verbose "& (& $PSScriptRoot/Get-NuGetTool.ps1) install Microsoft.DiaSymReader.Pdb2Pdb -version $version -PackageSaveMode nuspec -OutputDirectory $baseDir -Source https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json | Out-Null"
|
||||
& (& $PSScriptRoot/Get-NuGetTool.ps1) install Microsoft.DiaSymReader.Pdb2Pdb -version $version -PackageSaveMode nuspec -OutputDirectory $baseDir -Source https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json | Out-Null
|
||||
}
|
||||
|
||||
$args = $DllPath,'/out',$OutputPath,'/nowarn','0021'
|
||||
if ($PdbPath) {
|
||||
$args += '/pdb',$PdbPath
|
||||
}
|
||||
$args = $DllPath,'/out',$OutputPath,'/nowarn','0021'
|
||||
if ($PdbPath) {
|
||||
$args += '/pdb',$PdbPath
|
||||
}
|
||||
|
||||
Write-Verbose "$pdb2pdbpath $args"
|
||||
& $pdb2pdbpath $args
|
||||
#}
|
||||
Write-Verbose "$pdb2pdbpath $args"
|
||||
& $pdb2pdbpath $args
|
||||
|
|
|
@ -0,0 +1,86 @@
|
|||
<#
|
||||
.SYNOPSIS
|
||||
Downloads the CodeCov.io uploader tool and returns the path to it.
|
||||
.PARAMETER AllowSkipVerify
|
||||
Allows skipping signature verification of the downloaded tool if gpg is not installed.
|
||||
#>
|
||||
[CmdletBinding()]
|
||||
Param(
|
||||
[switch]$AllowSkipVerify
|
||||
)
|
||||
|
||||
if ($IsMacOS) {
|
||||
$codeCovUrl = "https://uploader.codecov.io/latest/macos/codecov"
|
||||
$toolName = 'codecov'
|
||||
}
|
||||
elseif ($IsLinux) {
|
||||
$codeCovUrl = "https://uploader.codecov.io/latest/linux/codecov"
|
||||
$toolName = 'codecov'
|
||||
}
|
||||
else {
|
||||
$codeCovUrl = "https://uploader.codecov.io/latest/windows/codecov.exe"
|
||||
$toolName = 'codecov.exe'
|
||||
}
|
||||
|
||||
$shaSuffix = ".SHA256SUM"
|
||||
$sigSuffix = $shaSuffix + ".sig"
|
||||
|
||||
Function Get-FileFromWeb([Uri]$Uri, $OutDir) {
|
||||
$OutFile = Join-Path $OutDir $Uri.Segments[-1]
|
||||
if (!(Test-Path $OutFile)) {
|
||||
Write-Verbose "Downloading $Uri..."
|
||||
if (!(Test-Path $OutDir)) { New-Item -ItemType Directory -Path $OutDir | Out-Null }
|
||||
try {
|
||||
(New-Object System.Net.WebClient).DownloadFile($Uri, $OutFile)
|
||||
} finally {
|
||||
# This try/finally causes the script to abort
|
||||
}
|
||||
}
|
||||
|
||||
$OutFile
|
||||
}
|
||||
|
||||
$toolsPath = & "$PSScriptRoot\Get-TempToolsPath.ps1"
|
||||
$binaryToolsPath = Join-Path $toolsPath codecov
|
||||
$testingPath = Join-Path $binaryToolsPath unverified
|
||||
$finalToolPath = Join-Path $binaryToolsPath $toolName
|
||||
|
||||
if (!(Test-Path $finalToolPath)) {
|
||||
if (Test-Path $testingPath) {
|
||||
Remove-Item -Recurse -Force $testingPath # ensure we download all matching files
|
||||
}
|
||||
$tool = Get-FileFromWeb $codeCovUrl $testingPath
|
||||
$sha = Get-FileFromWeb "$codeCovUrl$shaSuffix" $testingPath
|
||||
$sig = Get-FileFromWeb "$codeCovUrl$sigSuffix" $testingPath
|
||||
$key = Get-FileFromWeb https://keybase.io/codecovsecurity/pgp_keys.asc $testingPath
|
||||
|
||||
if ((Get-Command gpg -ErrorAction SilentlyContinue)) {
|
||||
Write-Host "Importing codecov key" -ForegroundColor Yellow
|
||||
gpg --import $key
|
||||
Write-Host "Verifying signature on codecov hash" -ForegroundColor Yellow
|
||||
gpg --verify $sig $sha
|
||||
} else {
|
||||
if ($AllowSkipVerify) {
|
||||
Write-Warning "gpg not found. Unable to verify hash signature."
|
||||
} else {
|
||||
throw "gpg not found. Unable to verify hash signature. Install gpg or add -AllowSkipVerify to override."
|
||||
}
|
||||
}
|
||||
|
||||
Write-Host "Verifying hash on downloaded tool" -ForegroundColor Yellow
|
||||
$actualHash = (Get-FileHash -Path $tool -Algorithm SHA256).Hash
|
||||
$expectedHash = (Get-Content $sha).Split()[0]
|
||||
if ($actualHash -ne $expectedHash) {
|
||||
# Validation failed. Delete the tool so we can't execute it.
|
||||
#Remove-Item $codeCovPath
|
||||
throw "codecov uploader tool failed signature validation."
|
||||
}
|
||||
|
||||
Copy-Item $tool $finalToolPath
|
||||
|
||||
if ($IsMacOS -or $IsLinux) {
|
||||
chmod u+x $finalToolPath
|
||||
}
|
||||
}
|
||||
|
||||
return $finalToolPath
|
|
@ -0,0 +1,26 @@
|
|||
<#
|
||||
.SYNOPSIS
|
||||
Look up the pull request URL of the insertion PR.
|
||||
#>
|
||||
$stagingFolder = $env:BUILD_STAGINGDIRECTORY
|
||||
if (!$stagingFolder) {
|
||||
$stagingFolder = $env:SYSTEM_DEFAULTWORKINGDIRECTORY
|
||||
if (!$stagingFolder) {
|
||||
Write-Error "This script must be run in an Azure Pipeline."
|
||||
exit 1
|
||||
}
|
||||
}
|
||||
$markdownFolder = Join-Path $stagingFolder (Join-Path 'MicroBuild' 'Output')
|
||||
$markdownFile = Join-Path $markdownFolder 'PullRequestUrl.md'
|
||||
if (!(Test-Path $markdownFile)) {
|
||||
Write-Error "This script should be run after the MicroBuildInsertVsPayload task."
|
||||
exit 2
|
||||
}
|
||||
|
||||
$insertionPRUrl = Get-Content $markdownFile
|
||||
if (!($insertionPRUrl -match 'https:.+?/pullrequest/(\d+)')) {
|
||||
Write-Error "Failed to parse pull request URL: $insertionPRUrl"
|
||||
exit 3
|
||||
}
|
||||
|
||||
$Matches[1]
|
|
@ -18,7 +18,7 @@ Write-Progress -Activity $ActivityName -CurrentOperation "Discovery PDB files"
|
|||
$PDBs = Get-ChildItem -rec "$Path/*.pdb"
|
||||
|
||||
# Filter PDBs to product OR test related.
|
||||
$testregex = "unittest|tests"
|
||||
$testregex = "unittest|tests|\.test\."
|
||||
|
||||
Write-Progress -Activity $ActivityName -CurrentOperation "De-duplicating symbols"
|
||||
$PDBsByHash = @{}
|
||||
|
@ -49,8 +49,13 @@ $PDBs |% {
|
|||
$BinaryImagePath = $dllPath
|
||||
} elseif (Test-Path $exePath) {
|
||||
$BinaryImagePath = $exePath
|
||||
} else {
|
||||
Write-Warning "`"$_`" found with no matching binary file."
|
||||
$BinaryImagePath = $null
|
||||
}
|
||||
|
||||
Write-Output $BinaryImagePath
|
||||
Write-Output $_.FullName
|
||||
if ($BinaryImagePath) {
|
||||
Write-Output $BinaryImagePath
|
||||
Write-Output $_.FullName
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,6 +11,8 @@
|
|||
The directory to install the package to. By default, it uses the Packages folder at the root of the repo.
|
||||
.PARAMETER ConfigFile
|
||||
The nuget.config file to use. By default, it uses :/nuget.config.
|
||||
.OUTPUTS
|
||||
System.String. The path to the installed package.
|
||||
#>
|
||||
[CmdletBinding(SupportsShouldProcess=$true,ConfirmImpact='Low')]
|
||||
Param(
|
||||
|
@ -45,6 +47,9 @@ try {
|
|||
$p = Start-Process $nugetPath $nugetArgs -NoNewWindow -Wait -PassThru
|
||||
if ($p.ExitCode -ne 0) { throw }
|
||||
}
|
||||
|
||||
# Provide the path to the installed package directory to our caller.
|
||||
Write-Output (Get-ChildItem "$PackagesDir\$PackageId.*")[0].FullName
|
||||
} finally {
|
||||
Pop-Location
|
||||
}
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
#!/usr/bin/env pwsh
|
||||
|
||||
<#
|
||||
.SYNOPSIS
|
||||
Merges code coverage reports.
|
||||
.PARAMETER Path
|
||||
The path(s) to search for Cobertura code coverage reports.
|
||||
.PARAMETER Format
|
||||
The format for the merged result. The default is Cobertura
|
||||
.PARAMETER OutputDir
|
||||
The directory the merged result will be written to. The default is `coveragereport` in the root of this repo.
|
||||
#>
|
||||
[CmdletBinding()]
|
||||
Param(
|
||||
[Parameter(Mandatory=$true)]
|
||||
[string[]]$Path,
|
||||
[ValidateSet('Badges', 'Clover', 'Cobertura', 'CsvSummary', 'Html', 'Html_Dark', 'Html_Light', 'HtmlChart', 'HtmlInline', 'HtmlInline_AzurePipelines', 'HtmlInline_AzurePipelines_Dark', 'HtmlInline_AzurePipelines_Light', 'HtmlSummary', 'JsonSummary', 'Latex', 'LatexSummary', 'lcov', 'MarkdownSummary', 'MHtml', 'PngChart', 'SonarQube', 'TeamCitySummary', 'TextSummary', 'Xml', 'XmlSummary')]
|
||||
[string]$Format='Cobertura',
|
||||
[string]$OutputFile=("$PSScriptRoot/../coveragereport/merged.cobertura.xml")
|
||||
)
|
||||
|
||||
$RepoRoot = [string](Resolve-Path $PSScriptRoot/..)
|
||||
|
||||
if (!(Test-Path $RepoRoot/obj/dotnet-coverage*)) {
|
||||
dotnet tool install --tool-path $RepoRoot/obj dotnet-coverage --version 17.4.3 --configfile $PSScriptRoot/justnugetorg.nuget.config
|
||||
}
|
||||
|
||||
Write-Verbose "Searching $Path for *.cobertura.xml files"
|
||||
$reports = Get-ChildItem -Recurse $Path -Filter *.cobertura.xml
|
||||
|
||||
if ($reports) {
|
||||
$reports |% { $_.FullName } |% {
|
||||
# In addition to replacing {reporoot}, we also normalize on one kind of slash so that the report aggregates data for a file whether data was collected on Windows or not.
|
||||
$xml = [xml](Get-Content -Path $_)
|
||||
$xml.coverage.packages.package.classes.class |? { $_.filename} |% {
|
||||
$_.filename = $_.filename.Replace('{reporoot}', $RepoRoot).Replace([IO.Path]::AltDirectorySeparatorChar, [IO.Path]::DirectorySeparatorChar)
|
||||
}
|
||||
|
||||
$xml.Save($_)
|
||||
}
|
||||
|
||||
$Inputs = $reports |% { Resolve-Path -relative $_.FullName }
|
||||
|
||||
if (Split-Path $OutputFile) {
|
||||
New-Item -Type Directory -Path (Split-Path $OutputFile) | Out-Null
|
||||
}
|
||||
|
||||
& "$RepoRoot/obj/dotnet-coverage" merge $Inputs -o $OutputFile -f cobertura
|
||||
} else {
|
||||
Write-Error "No reports found to merge."
|
||||
}
|
|
@ -0,0 +1,57 @@
|
|||
[CmdletBinding(SupportsShouldProcess = $true)]
|
||||
param(
|
||||
[Parameter(Mandatory=$true)]
|
||||
$AccessToken,
|
||||
[Parameter(Mandatory=$true)]
|
||||
$Markdown,
|
||||
[ValidateSet('Active','ByDesign','Closed','Fixed','Pending','Unknown','WontFix')]
|
||||
$CommentState='Active'
|
||||
)
|
||||
|
||||
# See https://docs.microsoft.com/en-us/dotnet/api/microsoft.teamfoundation.sourcecontrol.webapi.commentthreadstatus?view=azure-devops-dotnet
|
||||
if ($CommentState -eq 'Active') {
|
||||
$StatusCode = 1
|
||||
} elseif ($CommentState -eq 'ByDesign') {
|
||||
$StatusCode = 5
|
||||
} elseif ($CommentState -eq 'Closed') {
|
||||
$StatusCode = 4
|
||||
} elseif ($CommentState -eq 'Fixed') {
|
||||
$StatusCode = 2
|
||||
} elseif ($CommentState -eq 'Pending') {
|
||||
$StatusCode = 6
|
||||
} elseif ($CommentState -eq 'Unknown') {
|
||||
$StatusCode = 0
|
||||
} elseif ($CommentState -eq 'WontFix') {
|
||||
$StatusCode = 3
|
||||
}
|
||||
|
||||
# Build the JSON body up
|
||||
$body = ConvertTo-Json @{
|
||||
comments = @(@{
|
||||
parentCommentId = 0
|
||||
content = $Markdown
|
||||
commentType = 1
|
||||
})
|
||||
status = $StatusCode
|
||||
}
|
||||
|
||||
Write-Verbose "Posting JSON payload: `n$Body"
|
||||
|
||||
# Post the message to the Pull Request
|
||||
# https://docs.microsoft.com/en-us/rest/api/azure/devops/git/pull%20request%20threads?view=azure-devops-rest-5.1
|
||||
$url = "$($env:SYSTEM_TEAMFOUNDATIONCOLLECTIONURI)$env:SYSTEM_TEAMPROJECTID/_apis/git/repositories/$($env:BUILD_REPOSITORY_NAME)/pullRequests/$($env:SYSTEM_PULLREQUEST_PULLREQUESTID)/threads?api-version=5.1"
|
||||
if ($PSCmdlet.ShouldProcess($url, 'Post comment via REST call')) {
|
||||
try {
|
||||
if (!$env:SYSTEM_TEAMFOUNDATIONCOLLECTIONURI) {
|
||||
Write-Error "Posting to the pull request requires that the script is running in an Azure Pipelines context."
|
||||
exit 1
|
||||
}
|
||||
Write-Host "Posting PR comment to: $url"
|
||||
Invoke-RestMethod -Uri $url -Method POST -Headers @{Authorization = "Bearer $AccessToken"} -Body $Body -ContentType application/json
|
||||
}
|
||||
catch {
|
||||
Write-Error $_
|
||||
Write-Error $_.Exception.Message
|
||||
exit 2
|
||||
}
|
||||
}
|
|
@ -14,19 +14,24 @@ Get-ChildItem "$ArtifactStagingFolder\*.pdb" -Recurse |% {
|
|||
$BinaryImagePath = $dllPath
|
||||
} elseif (Test-Path $exePath) {
|
||||
$BinaryImagePath = $exePath
|
||||
} else {
|
||||
Write-Warning "`"$_`" found with no matching binary file."
|
||||
$BinaryImagePath = $null
|
||||
}
|
||||
|
||||
# Convert the PDB to legacy Windows PDBs
|
||||
Write-Host "Converting PDB for $_" -ForegroundColor DarkGray
|
||||
$WindowsPdbDir = "$($_.Directory.FullName)\$WindowsPdbSubDirName"
|
||||
if (!(Test-Path $WindowsPdbDir)) { mkdir $WindowsPdbDir | Out-Null }
|
||||
$legacyPdbPath = "$WindowsPdbDir\$($_.BaseName).pdb"
|
||||
& "$PSScriptRoot\Convert-PDB.ps1" -DllPath $BinaryImagePath -PdbPath $_ -OutputPath $legacyPdbPath
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Warning "PDB conversion of `"$_`" failed."
|
||||
}
|
||||
if ($BinaryImagePath) {
|
||||
# Convert the PDB to legacy Windows PDBs
|
||||
Write-Host "Converting PDB for $_" -ForegroundColor DarkGray
|
||||
$WindowsPdbDir = "$($_.Directory.FullName)\$WindowsPdbSubDirName"
|
||||
if (!(Test-Path $WindowsPdbDir)) { mkdir $WindowsPdbDir | Out-Null }
|
||||
$legacyPdbPath = "$WindowsPdbDir\$($_.BaseName).pdb"
|
||||
& "$PSScriptRoot\Convert-PDB.ps1" -DllPath $BinaryImagePath -PdbPath $_ -OutputPath $legacyPdbPath
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Warning "PDB conversion of `"$_`" failed."
|
||||
}
|
||||
|
||||
Move-Item $legacyPdbPath $_ -Force
|
||||
Move-Item $legacyPdbPath $_ -Force
|
||||
}
|
||||
}
|
||||
|
||||
Write-Host "##vso[artifact.upload containerfolder=symbols-legacy;artifactname=symbols-legacy;]$ArtifactStagingFolder"
|
||||
|
|
|
@ -0,0 +1,52 @@
|
|||
trigger: none # We only want to trigger manually or based on resources
|
||||
pr: none
|
||||
|
||||
# Source archival requirements come from a compliance tenet. Review a sample task here: https://devdiv.visualstudio.com/DevDiv/_workitems/edit/1550985
|
||||
# Source code should be archived within 30 days of the release date, and at least every quarter if your product is releasing more than once every 6 months.
|
||||
# If your sources on GitHub are public open source project, then using GitHub Public Archive is sufficient.
|
||||
schedules:
|
||||
- cron: "13 13 13 */3 *" # Every three months
|
||||
displayName: Periodic source archival
|
||||
branches:
|
||||
include:
|
||||
- main
|
||||
|
||||
parameters:
|
||||
- name: notes
|
||||
displayName: Notes to include in the SCA request
|
||||
type: string
|
||||
default: ' ' # optional parameters require a non-empty default.
|
||||
- name: whatif
|
||||
displayName: Only simulate the request
|
||||
type: boolean
|
||||
default: false
|
||||
|
||||
variables:
|
||||
- group: VS Core team # Expected to provide ManagerAlias, SourceCodeArchivalUri
|
||||
|
||||
pool:
|
||||
name: AzurePipelines-EO
|
||||
vmImage: AzurePipelinesUbuntu20.04compliant
|
||||
|
||||
steps:
|
||||
- checkout: self
|
||||
clean: true
|
||||
fetchDepth: 0
|
||||
- powershell: tools/Install-DotNetSdk.ps1
|
||||
displayName: ⚙ Install .NET SDK
|
||||
- powershell: azure-pipelines/variables/_pipelines.ps1
|
||||
failOnStderr: true
|
||||
displayName: ⚙ Set pipeline variables based on source
|
||||
- powershell: >
|
||||
$TeamAlias = '$(TeamEmail)'.Substring(0, '$(TeamEmail)'.IndexOf('@'))
|
||||
|
||||
azure-pipelines/Archive-SourceCode.ps1
|
||||
-ManagerAlias '$(ManagerAlias)'
|
||||
-TeamAlias $TeamAlias
|
||||
-BusinessGroupName '$(BusinessGroupName)'
|
||||
-ProductName '$(SymbolsFeatureName)'
|
||||
-ProductLanguage English
|
||||
-Notes '${{ parameters.notes }}'
|
||||
-Verbose
|
||||
-WhatIf:$${{ parameters.whatif }}
|
||||
displayName: 🗃️ Submit archival request
|
|
@ -1,13 +1,15 @@
|
|||
# This artifact captures everything needed to insert into VS (NuGet packages, insertion metadata, etc.)
|
||||
|
||||
<#
|
||||
.PARAMETER SbomNotRequired
|
||||
Indicates that returning the artifacts available is preferable to nothing at all when the SBOM has not yet been generated.
|
||||
#>
|
||||
[CmdletBinding()]
|
||||
Param (
|
||||
[switch]$SbomNotRequired
|
||||
)
|
||||
|
||||
if ($IsMacOS -or $IsLinux) {
|
||||
# We only package up for insertions on Windows agents since they are where optprof can happen.
|
||||
Write-Verbose "Skipping VSInsertion artifact since we're not on Windows."
|
||||
return @{}
|
||||
}
|
||||
|
||||
$RepoRoot = [System.IO.Path]::GetFullPath("$PSScriptRoot\..\..")
|
||||
$BuildConfiguration = $env:BUILDCONFIGURATION
|
||||
if (!$BuildConfiguration) {
|
||||
|
@ -16,10 +18,10 @@ if (!$BuildConfiguration) {
|
|||
|
||||
$PackagesRoot = "$RepoRoot/bin/Packages/$BuildConfiguration/NuGet"
|
||||
|
||||
# This artifact is not ready if we're running on the devdiv AzDO account and we don't have an SBOM yet.
|
||||
if ($env:SYSTEM_COLLECTIONID -eq '011b8bdf-6d56-4f87-be0d-0092136884d9' -and -not (Test-Path $PackagesRoot/_manifest) -and -not $SbomNotRequired) { return @{} }
|
||||
|
||||
if (!(Test-Path $PackagesRoot)) { return @{} }
|
||||
if (!(Test-Path $PackagesRoot)) {
|
||||
Write-Warning "Skipping because packages haven't been built yet."
|
||||
return @{}
|
||||
}
|
||||
|
||||
@{
|
||||
"$PackagesRoot" = (Get-ChildItem $PackagesRoot -Recurse)
|
||||
|
|
|
@ -12,9 +12,10 @@
|
|||
Value = an array of paths (absolute or relative to the BaseDirectory) to files to include in the artifact.
|
||||
FileInfo objects are also allowed.
|
||||
.PARAMETER Force
|
||||
Executes artifact scripts even if they have already been uploaded.
|
||||
Executes artifact scripts even if they have already been staged.
|
||||
#>
|
||||
|
||||
[CmdletBinding(SupportsShouldProcess = $true)]
|
||||
param (
|
||||
[string]$ArtifactNameSuffix,
|
||||
[switch]$Force
|
||||
|
@ -28,15 +29,16 @@ Function EnsureTrailingSlash($path) {
|
|||
$path.Replace('\', [IO.Path]::DirectorySeparatorChar)
|
||||
}
|
||||
|
||||
Function Test-ArtifactUploaded($artifactName) {
|
||||
$varName = "ARTIFACTUPLOADED_$($artifactName.ToUpper())"
|
||||
Function Test-ArtifactStaged($artifactName) {
|
||||
$varName = "ARTIFACTSTAGED_$($artifactName.ToUpper())"
|
||||
Test-Path "env:$varName"
|
||||
}
|
||||
|
||||
Get-ChildItem "$PSScriptRoot\*.ps1" -Exclude "_*" -Recurse | % {
|
||||
$ArtifactName = $_.BaseName
|
||||
if ($Force -or !(Test-ArtifactUploaded($ArtifactName + $ArtifactNameSuffix))) {
|
||||
if ($Force -or !(Test-ArtifactStaged($ArtifactName + $ArtifactNameSuffix))) {
|
||||
$totalFileCount = 0
|
||||
Write-Verbose "Collecting file list for artifact $($_.BaseName)"
|
||||
$fileGroups = & $_
|
||||
if ($fileGroups) {
|
||||
$fileGroups.GetEnumerator() | % {
|
||||
|
@ -65,6 +67,6 @@ Get-ChildItem "$PSScriptRoot\*.ps1" -Exclude "_*" -Recurse | % {
|
|||
Write-Warning "No files found for the `"$ArtifactName`" artifact."
|
||||
}
|
||||
} else {
|
||||
Write-Host "Skipping $ArtifactName because it has already been uploaded." -ForegroundColor DarkGray
|
||||
Write-Host "Skipping $ArtifactName because it has already been staged." -ForegroundColor DarkGray
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,15 +1,44 @@
|
|||
# This script translates all the artifacts described by _all.ps1
|
||||
# into commands that instruct Azure Pipelines to actually collect those artifacts.
|
||||
<#
|
||||
.SYNOPSIS
|
||||
This script translates all the artifacts described by _all.ps1
|
||||
into commands that instruct Azure Pipelines to actually collect those artifacts.
|
||||
#>
|
||||
|
||||
[CmdletBinding()]
|
||||
param (
|
||||
[string]$ArtifactNameSuffix
|
||||
[string]$ArtifactNameSuffix,
|
||||
[switch]$StageOnly
|
||||
)
|
||||
|
||||
& "$PSScriptRoot/_stage_all.ps1" -ArtifactNameSuffix $ArtifactNameSuffix |% {
|
||||
Write-Host "##vso[artifact.upload containerfolder=$($_.Name);artifactname=$($_.Name);]$($_.Path)"
|
||||
Function Set-PipelineVariable($name, $value) {
|
||||
if ((Test-Path "Env:\$name") -and (Get-Item "Env:\$name").Value -eq $value) {
|
||||
return # already set
|
||||
}
|
||||
|
||||
#New-Item -Path "Env:\$name".ToUpper() -Value $value -Force | Out-Null
|
||||
Write-Host "##vso[task.setvariable variable=$name]$value"
|
||||
}
|
||||
|
||||
Function Test-ArtifactUploaded($artifactName) {
|
||||
$varName = "ARTIFACTUPLOADED_$($artifactName.ToUpper())"
|
||||
Test-Path "env:$varName"
|
||||
}
|
||||
|
||||
& "$PSScriptRoot/_stage_all.ps1" -ArtifactNameSuffix $ArtifactNameSuffix |% {
|
||||
# Set a variable which will out-live this script so that a subsequent attempt to collect and upload artifacts
|
||||
# will skip this one from a check in the _all.ps1 script.
|
||||
$varName = "ARTIFACTUPLOADED_$($_.Name.ToUpper())"
|
||||
Write-Host "##vso[task.setvariable variable=$varName]true"
|
||||
Set-PipelineVariable "ARTIFACTSTAGED_$($_.Name.ToUpper())" 'true'
|
||||
Write-Host "Staged artifact $($_.Name) to $($_.Path)"
|
||||
|
||||
if (!$StageOnly) {
|
||||
if (Test-ArtifactUploaded $_.Name) {
|
||||
Write-Host "Skipping $($_.Name) because it has already been uploaded." -ForegroundColor DarkGray
|
||||
} else {
|
||||
Write-Host "##vso[artifact.upload containerfolder=$($_.Name);artifactname=$($_.Name);]$($_.Path)"
|
||||
|
||||
# Set a variable which will out-live this script so that a subsequent attempt to collect and upload artifacts
|
||||
# will skip this one from a check in the _all.ps1 script.
|
||||
Set-PipelineVariable "ARTIFACTUPLOADED_$($_.Name.ToUpper())" 'true'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,11 @@
|
|||
# This script links all the artifacts described by _all.ps1
|
||||
# into a staging directory, reading for uploading to a cloud build artifact store.
|
||||
# It returns a sequence of objects with Name and Path properties.
|
||||
<#
|
||||
.SYNOPSIS
|
||||
This script links all the artifacts described by _all.ps1
|
||||
into a staging directory, reading for uploading to a cloud build artifact store.
|
||||
It returns a sequence of objects with Name and Path properties.
|
||||
#>
|
||||
|
||||
[CmdletBinding()]
|
||||
param (
|
||||
[string]$ArtifactNameSuffix
|
||||
)
|
||||
|
@ -21,7 +25,6 @@ function Create-SymbolicLink {
|
|||
if (Test-Path $Link) { Remove-Item $Link }
|
||||
$LinkContainer = Split-Path $Link -Parent
|
||||
if (!(Test-Path $LinkContainer)) { mkdir $LinkContainer }
|
||||
Write-Verbose "Linking $Link to $Target"
|
||||
if ($IsMacOS -or $IsLinux) {
|
||||
ln $Target $Link | Out-Null
|
||||
} else {
|
||||
|
@ -43,7 +46,13 @@ $Artifacts |% {
|
|||
}
|
||||
}
|
||||
|
||||
$Artifacts |% { "$($_.ArtifactName)$ArtifactNameSuffix" } | Get-Unique |% {
|
||||
$ArtifactNames = $Artifacts |% { "$($_.ArtifactName)$ArtifactNameSuffix" }
|
||||
$ArtifactNames += Get-ChildItem env:ARTIFACTSTAGED_* |% {
|
||||
# Return from ALLCAPS to the actual capitalization used for the artifact.
|
||||
$artifactNameAllCaps = "$($_.Name.Substring('ARTIFACTSTAGED_'.Length))"
|
||||
(Get-ChildItem $ArtifactStagingFolder\$artifactNameAllCaps* -Filter $artifactNameAllCaps).Name
|
||||
}
|
||||
$ArtifactNames | Get-Unique |% {
|
||||
$artifact = New-Object -TypeName PSObject
|
||||
Add-Member -InputObject $artifact -MemberType NoteProperty -Name Name -Value $_
|
||||
Add-Member -InputObject $artifact -MemberType NoteProperty -Name Path -Value (Join-Path $ArtifactStagingFolder $_)
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
$RepoRoot = [System.IO.Path]::GetFullPath("$PSScriptRoot\..\..")
|
||||
|
||||
$coverageFiles = @(Get-ChildItem "$RepoRoot/test/*.cobertura.xml" -Recurse | Where {$_.FullName -notlike "*/In/*" -and $_.FullName -notlike "*\In\*" })
|
||||
|
||||
# Prepare code coverage reports for merging on another machine
|
||||
if ($env:SYSTEM_DEFAULTWORKINGDIRECTORY) {
|
||||
Write-Host "Substituting $env:SYSTEM_DEFAULTWORKINGDIRECTORY with `"{reporoot}`""
|
||||
$reports = Get-ChildItem "$RepoRoot/bin/coverage.*cobertura.xml" -Recurse
|
||||
$reports |% {
|
||||
$coverageFiles |% {
|
||||
$content = Get-Content -Path $_ |% { $_ -Replace [regex]::Escape($env:SYSTEM_DEFAULTWORKINGDIRECTORY), "{reporoot}" }
|
||||
Set-Content -Path $_ -Value $content -Encoding UTF8
|
||||
}
|
||||
|
@ -16,7 +17,7 @@ if (!((Test-Path $RepoRoot\bin) -and (Test-Path $RepoRoot\obj))) { return }
|
|||
|
||||
@{
|
||||
$RepoRoot = (
|
||||
@(Get-ChildItem "$RepoRoot\bin\coverage.*cobertura.xml" -Recurse) +
|
||||
$coverageFiles +
|
||||
(Get-ChildItem "$RepoRoot\obj\*.cs" -Recurse)
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,16 +1,11 @@
|
|||
[CmdletBinding()]
|
||||
Param(
|
||||
)
|
||||
|
||||
$result = @{}
|
||||
|
||||
if ($env:AGENT_TEMPDIRECTORY) {
|
||||
# The DotNetCoreCLI uses an alternate location to publish these files
|
||||
$guidRegex = '^[a-f0-9]{8}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{12}$'
|
||||
$result[$env:AGENT_TEMPDIRECTORY] = (Get-ChildItem $env:AGENT_TEMPDIRECTORY -Directory |? { $_.Name -match $guidRegex } |% {
|
||||
Get-ChildItem "$($_.FullName)\dotnet*.dmp","$($_.FullName)\*_crashdump.dmp","$($_.FullName)\testhost*.dmp","$($_.FullName)\Sequence_*.xml" -Recurse
|
||||
});
|
||||
}
|
||||
else {
|
||||
$testRoot = Resolve-Path "$PSScriptRoot\..\..\test"
|
||||
$result[$testRoot] = (Get-ChildItem "$testRoot\TestResults" -Recurse -Directory | Get-ChildItem -Recurse -File)
|
||||
}
|
||||
$testRoot = Resolve-Path "$PSScriptRoot\..\..\test"
|
||||
$result[$testRoot] = (Get-ChildItem "$testRoot\TestResults" -Recurse -Directory | Get-ChildItem -Recurse -File)
|
||||
|
||||
$testlogsPath = "$env:BUILD_ARTIFACTSTAGINGDIRECTORY\test_logs"
|
||||
if (Test-Path $testlogsPath) {
|
||||
|
|
|
@ -4,19 +4,27 @@ parameters:
|
|||
default:
|
||||
vmImage: windows-2022
|
||||
- name: includeMacOS
|
||||
- name: RunTests
|
||||
type: boolean
|
||||
default: true
|
||||
- name: EnableCompliance
|
||||
type: boolean
|
||||
default: true
|
||||
- name: EnableAPIScan
|
||||
type: boolean
|
||||
default: false
|
||||
default: true
|
||||
|
||||
jobs:
|
||||
- job: Windows
|
||||
pool: ${{ parameters.windowsPool }}
|
||||
timeoutInMinutes: 180 # Give plenty of time due to real signing
|
||||
variables:
|
||||
- ${{ if eq(variables['system.collectionId'], '011b8bdf-6d56-4f87-be0d-0092136884d9') }}:
|
||||
# https://dev.azure.com/devdiv/DevDiv/_wiki/wikis/DevDiv.wiki/25351/APIScan-step-by-step-guide-to-setting-up-a-Pipeline
|
||||
- group: VSCloudServices-APIScan
|
||||
- group: VSCloudServices-APIScan # Expected to provide ApiScanClientId, ApiScanSecret, ApiScanTenant
|
||||
steps:
|
||||
- checkout: self
|
||||
fetchDepth: 0 # avoid shallow clone so nbgv can do its work.
|
||||
clean: true
|
||||
|
||||
- ${{ if eq(variables['Build.Reason'], 'Schedule') }}:
|
||||
|
@ -25,16 +33,19 @@ jobs:
|
|||
- template: install-dependencies.yml
|
||||
|
||||
- powershell: '& (./azure-pipelines/Get-nbgv.ps1) cloud -ca'
|
||||
displayName: Set build number
|
||||
displayName: ⚙ Set build number
|
||||
|
||||
- ${{ if eq(variables['system.collectionId'], '011b8bdf-6d56-4f87-be0d-0092136884d9') }}:
|
||||
- template: microbuild.before.yml
|
||||
|
||||
- template: dotnet.yml
|
||||
parameters:
|
||||
RunTests: ${{ parameters.RunTests }}
|
||||
|
||||
- ${{ if eq(variables['system.collectionId'], '011b8bdf-6d56-4f87-be0d-0092136884d9') }}:
|
||||
- template: microbuild.after.yml
|
||||
parameters:
|
||||
EnableCompliance: ${{ parameters.EnableCompliance }}
|
||||
EnableAPIScan: ${{ parameters.EnableAPIScan }}
|
||||
# Repeat this step to scoop up any artifacts that would only be collected after running microbuild.after.yml
|
||||
- powershell: azure-pipelines/artifacts/_pipelines.ps1 -ArtifactNameSuffix "-$(Agent.JobName)"
|
||||
|
@ -47,19 +58,25 @@ jobs:
|
|||
vmImage: Ubuntu 20.04
|
||||
steps:
|
||||
- checkout: self
|
||||
fetchDepth: 0 # avoid shallow clone so nbgv can do its work.
|
||||
clean: true
|
||||
- template: install-dependencies.yml
|
||||
- template: dotnet.yml
|
||||
parameters:
|
||||
RunTests: ${{ parameters.RunTests }}
|
||||
|
||||
- job: macOS
|
||||
condition: ${{ parameters.includeMacOS }}
|
||||
pool:
|
||||
vmImage: macOS-10.15
|
||||
vmImage: macOS-12
|
||||
steps:
|
||||
- checkout: self
|
||||
fetchDepth: 0 # avoid shallow clone so nbgv can do its work.
|
||||
clean: true
|
||||
- template: install-dependencies.yml
|
||||
- template: dotnet.yml
|
||||
parameters:
|
||||
RunTests: ${{ parameters.RunTests }}
|
||||
|
||||
- job: WrapUp
|
||||
dependsOn:
|
||||
|
@ -70,6 +87,7 @@ jobs:
|
|||
condition: succeededOrFailed()
|
||||
steps:
|
||||
- checkout: self
|
||||
fetchDepth: 0 # avoid shallow clone so nbgv can do its work.
|
||||
clean: true
|
||||
- template: install-dependencies.yml
|
||||
parameters:
|
||||
|
@ -77,6 +95,7 @@ jobs:
|
|||
- template: publish-symbols.yml
|
||||
parameters:
|
||||
includeMacOS: ${{ parameters.includeMacOS }}
|
||||
- template: publish-codecoverage.yml
|
||||
parameters:
|
||||
includeMacOS: ${{ parameters.includeMacOS }}
|
||||
- ${{ if parameters.RunTests }}:
|
||||
- template: publish-codecoverage.yml
|
||||
parameters:
|
||||
includeMacOS: ${{ parameters.includeMacOS }}
|
||||
|
|
|
@ -1,24 +1,60 @@
|
|||
#!/usr/bin/env pwsh
|
||||
|
||||
<#
|
||||
.SYNOPSIS
|
||||
Runs tests as they are run in cloud test runs.
|
||||
.PARAMETER Configuration
|
||||
The configuration within which to run tests
|
||||
.PARAMETER Agent
|
||||
The name of the agent. This is used in preparing test run titles.
|
||||
.PARAMETER PublishResults
|
||||
A switch to publish results to Azure Pipelines.
|
||||
.PARAMETER x86
|
||||
A switch to run the tests in an x86 process.
|
||||
.PARAMETER dotnet32
|
||||
The path to a 32-bit dotnet executable to use.
|
||||
#>
|
||||
[CmdletBinding()]
|
||||
Param(
|
||||
[string]$Configuration='Debug',
|
||||
[string]$Agent='Local',
|
||||
[switch]$PublishResults
|
||||
[switch]$PublishResults,
|
||||
[switch]$x86,
|
||||
[string]$dotnet32
|
||||
)
|
||||
|
||||
$RepoRoot = (Resolve-Path "$PSScriptRoot/..").Path
|
||||
$ArtifactStagingFolder = & "$PSScriptRoot/Get-ArtifactsStagingDirectory.ps1"
|
||||
|
||||
dotnet test $RepoRoot `
|
||||
$dotnet = 'dotnet'
|
||||
if ($x86) {
|
||||
$x86RunTitleSuffix = ", x86"
|
||||
if ($dotnet32) {
|
||||
$dotnet = $dotnet32
|
||||
} else {
|
||||
$dotnet32Possibilities = "$PSScriptRoot\../obj/tools/x86/.dotnet/dotnet.exe", "$env:AGENT_TOOLSDIRECTORY/x86/dotnet/dotnet.exe", "${env:ProgramFiles(x86)}\dotnet\dotnet.exe"
|
||||
$dotnet32Matches = $dotnet32Possibilities |? { Test-Path $_ }
|
||||
if ($dotnet32Matches) {
|
||||
$dotnet = Resolve-Path @($dotnet32Matches)[0]
|
||||
Write-Host "Running tests using `"$dotnet`"" -ForegroundColor DarkGray
|
||||
} else {
|
||||
Write-Error "Unable to find 32-bit dotnet.exe"
|
||||
return 1
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
& $dotnet test $RepoRoot `
|
||||
--no-build `
|
||||
-c $Configuration `
|
||||
--filter "TestCategory!=FailsInCloudTest" `
|
||||
-p:CollectCoverage=true `
|
||||
--collect "Code Coverage;Format=cobertura" `
|
||||
--settings "$PSScriptRoot/test.runsettings" `
|
||||
--blame-hang-timeout 60s `
|
||||
--blame-crash `
|
||||
-bl:"$ArtifactStagingFolder/build_logs/test.binlog" `
|
||||
--diag "$ArtifactStagingFolder/test_logs/diag.log;TraceLevel=info" `
|
||||
--logger trx
|
||||
--logger trx `
|
||||
|
||||
$unknownCounter = 0
|
||||
Get-ChildItem -Recurse -Path $RepoRoot\test\*.trx |% {
|
||||
|
@ -26,16 +62,20 @@ Get-ChildItem -Recurse -Path $RepoRoot\test\*.trx |% {
|
|||
|
||||
if ($PublishResults) {
|
||||
$x = [xml](Get-Content -Path $_)
|
||||
$storage = $x.TestRun.TestDefinitions.GetElementsByTagName('UnitTest')[0].storage -replace '\\','/'
|
||||
if ($storage -match '/(?<tfm>net[^/]+)/(?:(?<rid>[^/]+)/)?(?<lib>[^/]+)\.dll$') {
|
||||
$runTitle = $null
|
||||
if ($x.TestRun.TestDefinitions -and $x.TestRun.TestDefinitions.GetElementsByTagName('UnitTest')) {
|
||||
$storage = $x.TestRun.TestDefinitions.GetElementsByTagName('UnitTest')[0].storage -replace '\\','/'
|
||||
if ($storage -match '/(?<tfm>net[^/]+)/(?:(?<rid>[^/]+)/)?(?<lib>[^/]+)\.dll$') {
|
||||
if ($matches.rid) {
|
||||
$runTitle = "$($matches.lib) ($($matches.tfm), $($matches.rid), $Agent)"
|
||||
} else {
|
||||
$runTitle = "$($matches.lib) ($($matches.tfm), $Agent)"
|
||||
$runTitle = "$($matches.lib) ($($matches.tfm)$x86RunTitleSuffix, $Agent)"
|
||||
}
|
||||
} else {
|
||||
$unknownCounter += 1;
|
||||
$runTitle = "unknown$unknownCounter ($Agent)";
|
||||
}
|
||||
}
|
||||
if (!$runTitle) {
|
||||
$unknownCounter += 1;
|
||||
$runTitle = "unknown$unknownCounter ($Agent$x86RunTitleSuffix)";
|
||||
}
|
||||
|
||||
Write-Host "##vso[results.publish type=VSTest;runTitle=$runTitle;publishRunAttachments=true;resultFiles=$_;failTaskOnFailedTests=true;testRunSystem=VSTS - PTR;]"
|
||||
|
|
|
@ -1,23 +1,30 @@
|
|||
parameters:
|
||||
RunTests:
|
||||
|
||||
steps:
|
||||
|
||||
- script: dotnet build -t:build,pack --no-restore -c $(BuildConfiguration) /bl:"$(Build.ArtifactStagingDirectory)/build_logs/build.binlog"
|
||||
displayName: dotnet build
|
||||
displayName: 🛠 dotnet build
|
||||
|
||||
- powershell: azure-pipelines/dotnet-test-cloud.ps1 -Configuration $(BuildConfiguration) -Agent $(Agent.JobName) -PublishResults
|
||||
displayName: dotnet test
|
||||
displayName: 🧪 dotnet test
|
||||
condition: and(succeeded(), ${{ parameters.RunTests }})
|
||||
|
||||
- powershell: azure-pipelines/variables/_pipelines.ps1
|
||||
failOnStderr: true
|
||||
displayName: Update pipeline variables based on build outputs
|
||||
displayName: ⚙ Update pipeline variables based on build outputs
|
||||
condition: succeededOrFailed()
|
||||
|
||||
- powershell: azure-pipelines/artifacts/_pipelines.ps1 -ArtifactNameSuffix "-$(Agent.JobName)"
|
||||
- powershell: azure-pipelines/artifacts/_pipelines.ps1 -ArtifactNameSuffix "-$(Agent.JobName)" -Verbose
|
||||
failOnStderr: true
|
||||
displayName: Publish artifacts
|
||||
displayName: 📢 Publish artifacts
|
||||
condition: succeededOrFailed()
|
||||
|
||||
- bash: bash <(curl -s https://codecov.io/bash)
|
||||
displayName: Publish code coverage results to codecov.io
|
||||
condition: ne(variables['codecov_token'], '')
|
||||
timeoutInMinutes: 3
|
||||
continueOnError: true
|
||||
- ${{ if and(ne(variables['codecov_token'], ''), parameters.RunTests) }}:
|
||||
- powershell: |
|
||||
$ArtifactStagingFolder = & "azure-pipelines/Get-ArtifactsStagingDirectory.ps1"
|
||||
$CoverageResultsFolder = Join-Path $ArtifactStagingFolder "coverageResults-$(Agent.JobName)"
|
||||
azure-pipelines/publish-CodeCov.ps1 -CodeCovToken "$(codecov_token)" -PathToCodeCoverage "$CoverageResultsFolder" -Name "$(Agent.JobName) Coverage Results" -Flags "$(Agent.JobName)Host,$(BuildConfiguration)"
|
||||
displayName: 📢 Publish code coverage results to codecov.io
|
||||
timeoutInMinutes: 3
|
||||
continueOnError: true
|
||||
|
|
|
@ -3,9 +3,11 @@ parameters:
|
|||
|
||||
steps:
|
||||
|
||||
- task: NuGetAuthenticate@0
|
||||
displayName: Authenticate NuGet feeds
|
||||
- task: NuGetAuthenticate@1
|
||||
displayName: 🔏 Authenticate NuGet feeds
|
||||
inputs:
|
||||
${{ if eq(variables['system.collectionId'], '011b8bdf-6d56-4f87-be0d-0092136884d9') }}:
|
||||
nuGetServiceConnections: azure-public/msft_consumption
|
||||
forceReinstallCredentialProvider: true
|
||||
|
||||
- powershell: |
|
||||
|
@ -17,9 +19,9 @@ steps:
|
|||
if (Get-Command mono -ErrorAction SilentlyContinue) {
|
||||
mono --version
|
||||
}
|
||||
displayName: Install prerequisites
|
||||
displayName: ⚙ Install prerequisites
|
||||
|
||||
- powershell: azure-pipelines/variables/_pipelines.ps1
|
||||
failOnStderr: true
|
||||
displayName: Set pipeline variables based on source
|
||||
displayName: ⚙ Set pipeline variables based on source
|
||||
name: SetPipelineVariables
|
||||
|
|
|
@ -1,29 +1,20 @@
|
|||
parameters:
|
||||
- name: EnableAPIScan
|
||||
type: boolean
|
||||
EnableCompliance:
|
||||
EnableAPIScan:
|
||||
|
||||
steps:
|
||||
- task: MicroBuildCodesignVerify@3
|
||||
displayName: Verify Signed Files
|
||||
displayName: 🔍 Verify Signed Files
|
||||
inputs:
|
||||
TargetFolders: |
|
||||
$(Build.SourcesDirectory)/bin/Packages/$(BuildConfiguration)/NuGet
|
||||
|
||||
- task: MicroBuildCleanup@1
|
||||
condition: succeededOrFailed()
|
||||
displayName: MicroBuild Cleanup
|
||||
|
||||
- task: ManifestGeneratorTask@0
|
||||
displayName: Software Bill of Materials generation
|
||||
inputs:
|
||||
BuildDropPath: $(System.DefaultWorkingDirectory)/bin/Microsoft.VisualStudio.Validation/$(BuildConfiguration)
|
||||
BuildComponentPath: $(System.DefaultWorkingDirectory)/obj/src/Microsoft.VisualStudio.Validation
|
||||
|
||||
- powershell: Copy-Item -Recurse "$(System.DefaultWorkingDirectory)/bin/Microsoft.VisualStudio.Validation/$(BuildConfiguration)/_manifest" "$(System.DefaultWorkingDirectory)/bin/Packages/$(BuildConfiguration)/NuGet"
|
||||
displayName: Publish Software Bill of Materials
|
||||
displayName: ⚙️ MicroBuild Cleanup
|
||||
|
||||
- task: Ref12Analyze@0
|
||||
displayName: Ref12 (Codex) Analyze
|
||||
displayName: 📑 Ref12 (Codex) Analyze
|
||||
inputs:
|
||||
codexoutputroot: $(Build.ArtifactStagingDirectory)\Codex
|
||||
workflowArguments: |
|
||||
|
@ -35,6 +26,7 @@ steps:
|
|||
condition: and(succeeded(), eq(variables['Build.SourceBranch'], 'refs/heads/main'), ne(variables['Build.Reason'], 'PullRequest'))
|
||||
continueOnError: true
|
||||
|
||||
- template: secure-development-tools.yml
|
||||
parameters:
|
||||
EnableAPIScan: ${{ parameters.EnableAPIScan }}
|
||||
- ${{ if eq(parameters.EnableCompliance, 'true') }}:
|
||||
- template: secure-development-tools.yml
|
||||
parameters:
|
||||
EnableAPIScan: ${{ parameters.EnableAPIScan }}
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
steps:
|
||||
- task: ComponentGovernanceComponentDetection@0
|
||||
displayName: Component Detection
|
||||
displayName: 🔍 Component Detection
|
||||
|
||||
- task: notice@0
|
||||
displayName: Generate NOTICE file
|
||||
displayName: 🛠️ Generate NOTICE file
|
||||
inputs:
|
||||
outputfile: $(System.DefaultWorkingDirectory)/obj/NOTICE
|
||||
outputformat: text
|
||||
|
@ -11,9 +11,13 @@ steps:
|
|||
- task: MicroBuildSigningPlugin@3
|
||||
inputs:
|
||||
signType: $(SignType)
|
||||
displayName: Install MicroBuild Signing Plugin
|
||||
zipSources: false
|
||||
displayName: 🔧 Install MicroBuild Signing Plugin
|
||||
|
||||
- task: MicroBuildSbomPlugin@1
|
||||
displayName: 🔧 Install MicroBuild Sbom Plugin
|
||||
|
||||
- task: MicroBuildLocalizationPlugin@3
|
||||
inputs:
|
||||
languages: $(LocLanguages)
|
||||
displayName: Install MicroBuild Localization Plugin
|
||||
displayName: 🔧 Install MicroBuild Localization Plugin
|
||||
|
|
|
@ -31,8 +31,16 @@ parameters:
|
|||
displayName: Build on macOS
|
||||
type: boolean
|
||||
default: false # macOS is often bogged down in Azure Pipelines
|
||||
- name: RunTests
|
||||
displayName: Run tests
|
||||
type: boolean
|
||||
default: true
|
||||
- name: EnableCompliance
|
||||
displayName: Run Compliance Tools
|
||||
type: boolean
|
||||
default: true
|
||||
- name: EnableAPIScan
|
||||
displayName: Run APIScan
|
||||
displayName: Include APIScan with Compliance tools
|
||||
type: boolean
|
||||
default: true
|
||||
|
||||
|
@ -45,67 +53,16 @@ stages:
|
|||
BuildConfiguration: Release
|
||||
NUGET_PACKAGES: $(Agent.TempDirectory)/.nuget/packages
|
||||
SignTypeSelection: ${{ parameters.SignTypeSelection }}
|
||||
Packaging.EnableSBOMSigning: true
|
||||
Packaging.EnableSBOMSigning: false
|
||||
Codeql.Enabled: true
|
||||
|
||||
jobs:
|
||||
- template: build.yml
|
||||
parameters:
|
||||
EnableCompliance: ${{ parameters.EnableCompliance }}
|
||||
EnableAPIScan: ${{ parameters.EnableAPIScan }}
|
||||
windowsPool: VSEngSS-MicroBuild2022-1ES
|
||||
includeMacOS: ${{ parameters.includeMacOS }}
|
||||
RunTests: ${{ parameters.RunTests }}
|
||||
|
||||
- stage: symbol_archive
|
||||
displayName: Symbol archival
|
||||
condition: and(succeeded(), eq(dependencies.Build.outputs['Windows.SetPipelineVariables.SignType'], 'Real'))
|
||||
jobs:
|
||||
- job: archive
|
||||
pool: VSEng-ReleasePool-1ES
|
||||
steps:
|
||||
- checkout: none
|
||||
- download: current
|
||||
artifact: Variables-Windows
|
||||
displayName: Download Variables-Windows artifact
|
||||
- task: PowerShell@2
|
||||
displayName: Set VSTS variables based on artifacts
|
||||
inputs:
|
||||
targetType: filePath
|
||||
filePath: $(Pipeline.Workspace)/Variables-Windows/_pipelines.ps1
|
||||
- download: current
|
||||
artifact: symbols-legacy
|
||||
displayName: Download symbols-legacy artifact
|
||||
- task: MicroBuildArchiveSymbols@1
|
||||
displayName: Archive symbols to Symweb
|
||||
inputs:
|
||||
SymbolsFeatureName: $(SymbolsFeatureName)
|
||||
SymbolsSymwebProject: VS
|
||||
SymbolsUncPath: \\cpvsbuild\drops\$(TeamName)\$(Build.DefinitionName)\$(Build.SourceBranchName)\$(Build.BuildId)\Symbols.Archival
|
||||
SymbolsEmailContacts: vsidemicrobuild
|
||||
SymbolsAgentPath: $(Pipeline.Workspace)/symbols-legacy
|
||||
- task: MicroBuildCleanup@1
|
||||
displayName: Send Telemetry
|
||||
|
||||
- stage: azure_public_vssdk_feed
|
||||
displayName: azure-public/vssdk feed
|
||||
condition: and(succeeded(), eq(dependencies.Build.outputs['Windows.SetPipelineVariables.SignType'], 'Real'))
|
||||
jobs:
|
||||
- job: push
|
||||
pool:
|
||||
name: AzurePipelines-EO
|
||||
vmImage: AzurePipelinesUbuntu20.04compliant
|
||||
steps:
|
||||
- checkout: none
|
||||
- download: current
|
||||
artifact: deployables-Windows
|
||||
displayName: Download deployables-Windows artifact
|
||||
- task: UseDotNet@2
|
||||
displayName: Install .NET SDK
|
||||
inputs:
|
||||
packageType: sdk
|
||||
version: 6.x
|
||||
- task: NuGetAuthenticate@0
|
||||
displayName: Authenticate NuGet feeds
|
||||
inputs:
|
||||
nuGetServiceConnections: azure-public/vssdk
|
||||
forceReinstallCredentialProvider: true
|
||||
- script: dotnet nuget push $(Pipeline.Workspace)/deployables-Windows/NuGet/*.nupkg -s https://pkgs.dev.azure.com/azure-public/vside/_packaging/vssdk/nuget/v3/index.json --api-key azdo --skip-duplicate
|
||||
displayName: Push nuget packages
|
||||
- template: prepare-insertion-stages.yml
|
||||
|
|
|
@ -0,0 +1,56 @@
|
|||
stages:
|
||||
- stage: symbol_archive
|
||||
displayName: Symbol archival
|
||||
condition: and(succeeded(), eq(dependencies.Build.outputs['Windows.SetPipelineVariables.SignType'], 'Real'))
|
||||
jobs:
|
||||
- job: archive
|
||||
pool: VSEng-ReleasePool-1ES
|
||||
steps:
|
||||
- checkout: none
|
||||
- download: current
|
||||
artifact: Variables-Windows
|
||||
displayName: Download Variables-Windows artifact
|
||||
- task: PowerShell@2
|
||||
displayName: Set pipeline variables based on artifacts
|
||||
inputs:
|
||||
targetType: filePath
|
||||
filePath: $(Pipeline.Workspace)/Variables-Windows/_pipelines.ps1
|
||||
- download: current
|
||||
artifact: symbols-legacy
|
||||
displayName: Download symbols-legacy artifact
|
||||
- task: MicroBuildArchiveSymbols@1
|
||||
displayName: Archive symbols to Symweb
|
||||
inputs:
|
||||
SymbolsFeatureName: $(SymbolsFeatureName)
|
||||
SymbolsSymwebProject: VS
|
||||
SymbolsUncPath: \\cpvsbuild\drops\$(TeamName)\$(Build.DefinitionName)\$(Build.SourceBranchName)\$(Build.BuildId)\Symbols.Archival
|
||||
SymbolsEmailContacts: vsidemicrobuild
|
||||
SymbolsAgentPath: $(Pipeline.Workspace)/symbols-legacy
|
||||
- task: MicroBuildCleanup@1
|
||||
displayName: Send Telemetry
|
||||
|
||||
- stage: azure_public_vssdk_feed
|
||||
displayName: azure-public/vssdk feed
|
||||
condition: and(succeeded(), eq(dependencies.Build.outputs['Windows.SetPipelineVariables.SignType'], 'Real'))
|
||||
jobs:
|
||||
- job: push
|
||||
pool:
|
||||
name: AzurePipelines-EO
|
||||
vmImage: AzurePipelinesUbuntu20.04compliant
|
||||
steps:
|
||||
- checkout: none
|
||||
- download: current
|
||||
artifact: deployables-Windows
|
||||
displayName: Download deployables-Windows artifact
|
||||
- task: UseDotNet@2
|
||||
displayName: Install .NET SDK
|
||||
inputs:
|
||||
packageType: sdk
|
||||
version: 6.x
|
||||
- task: NuGetAuthenticate@1
|
||||
displayName: Authenticate NuGet feeds
|
||||
inputs:
|
||||
nuGetServiceConnections: azure-public/vssdk
|
||||
forceReinstallCredentialProvider: true
|
||||
- script: dotnet nuget push $(Pipeline.Workspace)/deployables-Windows/NuGet/*.nupkg -s https://pkgs.dev.azure.com/azure-public/vside/_packaging/vssdk/nuget/v3/index.json --api-key azdo --skip-duplicate
|
||||
displayName: Push nuget packages
|
|
@ -0,0 +1,30 @@
|
|||
<#
|
||||
.SYNOPSIS
|
||||
Uploads code coverage to codecov.io
|
||||
.PARAMETER CodeCovToken
|
||||
Code coverage token to use
|
||||
.PARAMETER PathToCodeCoverage
|
||||
Path to root of code coverage files
|
||||
.PARAMETER Name
|
||||
Name to upload with codecoverge
|
||||
.PARAMETER Flags
|
||||
Flags to upload with codecoverge
|
||||
#>
|
||||
[CmdletBinding()]
|
||||
Param (
|
||||
[Parameter(Mandatory=$true)]
|
||||
[string]$CodeCovToken,
|
||||
[Parameter(Mandatory=$true)]
|
||||
[string]$PathToCodeCoverage,
|
||||
[string]$Name,
|
||||
[string]$Flags
|
||||
)
|
||||
|
||||
$RepoRoot = (Resolve-Path "$PSScriptRoot/..").Path
|
||||
|
||||
Get-ChildItem -Recurse -Path $PathToCodeCoverage -Filter "*.cobertura.xml" | % {
|
||||
$relativeFilePath = Resolve-Path -relative $_.FullName
|
||||
|
||||
Write-Host "Uploading: $relativeFilePath" -ForegroundColor Yellow
|
||||
& (& "$PSScriptRoot/Get-CodeCovTool.ps1") -t $CodeCovToken -f $relativeFilePath -R $RepoRoot -F $Flags -n $Name
|
||||
}
|
|
@ -4,32 +4,22 @@ parameters:
|
|||
steps:
|
||||
- download: current
|
||||
artifact: coverageResults-Windows
|
||||
displayName: Download Windows code coverage results
|
||||
displayName: 🔻 Download Windows code coverage results
|
||||
continueOnError: true
|
||||
- download: current
|
||||
artifact: coverageResults-Linux
|
||||
displayName: Download Linux code coverage results
|
||||
displayName: 🔻 Download Linux code coverage results
|
||||
continueOnError: true
|
||||
- download: current
|
||||
artifact: coverageResults-macOS
|
||||
displayName: Download macOS code coverage results
|
||||
displayName: 🔻 Download macOS code coverage results
|
||||
continueOnError: true
|
||||
condition: ${{ parameters.includeMacOS }}
|
||||
- powershell: |
|
||||
dotnet tool install --tool-path obj dotnet-reportgenerator-globaltool --version 4.8.5 --configfile azure-pipelines/justnugetorg.nuget.config
|
||||
Copy-Item -Recurse $(Pipeline.Workspace)/coverageResults-Windows/obj/* $(System.DefaultWorkingDirectory)/obj
|
||||
Write-Host 'Substituting {reporoot} with $(System.DefaultWorkingDirectory)'
|
||||
$reports = Get-ChildItem -Recurse '$(Pipeline.Workspace)/coverage.*cobertura.xml'
|
||||
$reports |% {
|
||||
$content = Get-Content -Path $_ |% { $_.Replace('{reporoot}', '$(System.DefaultWorkingDirectory)') }
|
||||
Set-Content -Path $_ -Value $content -Encoding UTF8
|
||||
}
|
||||
$Inputs = [string]::join(';', ($reports |% { Resolve-Path -relative $_ }))
|
||||
obj/reportgenerator -reports:"$Inputs" -targetdir:coveragereport -reporttypes:Cobertura
|
||||
displayName: Merge coverage
|
||||
condition: and(succeeded(), ${{ parameters.includeMacOS }})
|
||||
- powershell: azure-pipelines/Merge-CodeCoverage.ps1 -Path '$(Pipeline.Workspace)' -OutputFile coveragereport/merged.cobertura.xml -Format Cobertura -Verbose
|
||||
displayName: ⚙ Merge coverage
|
||||
- task: PublishCodeCoverageResults@1
|
||||
displayName: Publish code coverage results to Azure DevOps
|
||||
displayName: 📢 Publish code coverage results to Azure DevOps
|
||||
inputs:
|
||||
codeCoverageTool: cobertura
|
||||
summaryFileLocation: 'coveragereport/Cobertura.xml'
|
||||
summaryFileLocation: coveragereport/merged.cobertura.xml
|
||||
failIfCoverageEmpty: true
|
||||
|
|
|
@ -6,19 +6,19 @@ steps:
|
|||
inputs:
|
||||
artifact: symbols-Windows
|
||||
path: $(Pipeline.Workspace)/symbols/Windows
|
||||
displayName: Download Windows symbols
|
||||
displayName: 🔻 Download Windows symbols
|
||||
continueOnError: true
|
||||
- task: DownloadPipelineArtifact@2
|
||||
inputs:
|
||||
artifact: symbols-Linux
|
||||
path: $(Pipeline.Workspace)/symbols/Linux
|
||||
displayName: Download Linux symbols
|
||||
displayName: 🔻 Download Linux symbols
|
||||
continueOnError: true
|
||||
- task: DownloadPipelineArtifact@2
|
||||
inputs:
|
||||
artifact: symbols-macOS
|
||||
path: $(Pipeline.Workspace)/symbols/macOS
|
||||
displayName: Download macOS symbols
|
||||
displayName: 🔻 Download macOS symbols
|
||||
continueOnError: true
|
||||
condition: ${{ parameters.includeMacOS }}
|
||||
|
||||
|
@ -26,19 +26,19 @@ steps:
|
|||
inputs:
|
||||
artifact: test_symbols-Windows
|
||||
path: $(Pipeline.Workspace)/test_symbols/Windows
|
||||
displayName: Download Windows test symbols
|
||||
displayName: 🔻 Download Windows test symbols
|
||||
continueOnError: true
|
||||
- task: DownloadPipelineArtifact@2
|
||||
inputs:
|
||||
artifact: test_symbols-Linux
|
||||
path: $(Pipeline.Workspace)/test_symbols/Linux
|
||||
displayName: Download Linux test symbols
|
||||
displayName: 🔻 Download Linux test symbols
|
||||
continueOnError: true
|
||||
- task: DownloadPipelineArtifact@2
|
||||
inputs:
|
||||
artifact: test_symbols-macOS
|
||||
path: $(Pipeline.Workspace)/test_symbols/macOS
|
||||
displayName: Download macOS test symbols
|
||||
displayName: 🔻 Download macOS test symbols
|
||||
continueOnError: true
|
||||
condition: ${{ parameters.includeMacOS }}
|
||||
|
||||
|
@ -48,7 +48,7 @@ steps:
|
|||
SearchPattern: '**/*.pdb'
|
||||
IndexSources: false
|
||||
SymbolServerType: TeamServices
|
||||
displayName: Publish symbols
|
||||
displayName: 📢 Publish symbols
|
||||
|
||||
- task: PublishSymbols@2
|
||||
inputs:
|
||||
|
@ -56,7 +56,7 @@ steps:
|
|||
SearchPattern: '**/*.pdb'
|
||||
IndexSources: false
|
||||
SymbolServerType: TeamServices
|
||||
displayName: Publish test symbols
|
||||
displayName: 📢 Publish test symbols
|
||||
|
||||
- powershell: azure-pipelines/Publish-Legacy-Symbols.ps1 -Path $(Pipeline.Workspace)/symbols/Windows
|
||||
displayName: Publish symbols for symbol archival
|
||||
displayName: 📢 Publish symbols for symbol archival
|
||||
|
|
|
@ -10,7 +10,7 @@ resources:
|
|||
- auto-release
|
||||
|
||||
variables:
|
||||
- group: VS SDK feeds
|
||||
- group: VS SDK feeds # Expected to provide NuGetOrgApiKey
|
||||
|
||||
jobs:
|
||||
- job: release
|
||||
|
@ -26,18 +26,18 @@ jobs:
|
|||
} else {
|
||||
Write-Host "##vso[task.setvariable variable=IsPrerelease]false"
|
||||
}
|
||||
displayName: Set up pipeline
|
||||
displayName: ⚙ Set up pipeline
|
||||
- task: UseDotNet@2
|
||||
displayName: Install .NET SDK
|
||||
displayName: ⚙ Install .NET SDK
|
||||
inputs:
|
||||
packageType: sdk
|
||||
version: 6.x
|
||||
- download: CI
|
||||
artifact: deployables-Windows
|
||||
displayName: Download deployables-Windows artifact
|
||||
patterns: 'deployables-Windows/*'
|
||||
displayName: 🔻 Download deployables-Windows artifact
|
||||
patterns: 'deployables-Windows/NuGet/*'
|
||||
- task: GitHubRelease@1
|
||||
displayName: GitHub release (create)
|
||||
displayName: 📢 GitHub release (create)
|
||||
inputs:
|
||||
gitHubConnection: AArnott
|
||||
repositoryName: $(Build.Repository.Name)
|
||||
|
@ -52,9 +52,10 @@ jobs:
|
|||
changeLogType: issueBased
|
||||
changeLogLabels: |
|
||||
[
|
||||
{ "label" : "breaking change", "displayName" : "Breaking changes", "state" : "closed" },
|
||||
{ "label" : "bug", "displayName" : "Fixes", "state" : "closed" },
|
||||
{ "label" : "enhancement", "displayName": "Enhancements", "state" : "closed" }
|
||||
]
|
||||
- script: dotnet nuget push $(Pipeline.Workspace)/CI/deployables-Windows/NuGet/*.nupkg -s https://api.nuget.org/v3/index.json --api-key $(NuGetOrgApiKey) --skip-duplicate
|
||||
displayName: Push nuget packages
|
||||
displayName: 📦 Push packages to nuget.org
|
||||
condition: and(succeeded(), ne(variables['NuGetOrgApiKey'], ''))
|
||||
|
|
|
@ -1,21 +1,23 @@
|
|||
parameters:
|
||||
- name: EnableAPIScan
|
||||
type: boolean
|
||||
EnableAPIScan:
|
||||
|
||||
steps:
|
||||
|
||||
- powershell: echo "##vso[build.addbuildtag]compliance"
|
||||
displayName: 🏷️ Tag run with 'compliance'
|
||||
|
||||
- task: CredScan@3
|
||||
displayName: Run CredScan
|
||||
displayName: 🔍 Run CredScan
|
||||
|
||||
- task: PoliCheck@2
|
||||
displayName: Run PoliCheck
|
||||
displayName: 🔍 Run PoliCheck
|
||||
inputs:
|
||||
targetType: F
|
||||
targetArgument: $(System.DefaultWorkingDirectory)
|
||||
optionsUEPATH: $(System.DefaultWorkingDirectory)\azure-pipelines\PoliCheckExclusions.xml
|
||||
|
||||
- task: BinSkim@4
|
||||
displayName: Run BinSkim
|
||||
displayName: 🔍 Run BinSkim
|
||||
inputs:
|
||||
InputType: Basic
|
||||
Function: analyze
|
||||
|
@ -23,17 +25,18 @@ steps:
|
|||
AnalyzeTargetGlob: $(BinSkimTargets)
|
||||
|
||||
- task: CopyFiles@2
|
||||
displayName: Collect APIScan inputs
|
||||
displayName: 🔍 Collect APIScan inputs
|
||||
inputs:
|
||||
SourceFolder: $(Build.ArtifactStagingDirectory)/Symbols-$(Agent.JobName)
|
||||
# Exclude any patterns from the Contents (e.g. `!**/git2*`) that we have symbols for but do not need to run APIScan on.
|
||||
Contents: |
|
||||
**
|
||||
!**/arm64/**
|
||||
TargetFolder: $(Build.ArtifactStagingDirectory)/APIScanInputs
|
||||
condition: and(succeeded(), ${{ parameters.EnableAPIScan }}, ne(variables.ApiScanClientId, ''))
|
||||
|
||||
- task: APIScan@2
|
||||
displayName: Run APIScan
|
||||
displayName: 🔍 Run APIScan
|
||||
inputs:
|
||||
softwareFolder: $(Build.ArtifactStagingDirectory)/APIScanInputs
|
||||
softwareName: $(SymbolsFeatureName)
|
||||
|
@ -45,12 +48,12 @@ steps:
|
|||
AzureServicesAuthConnectionString: runAs=App;AppId=$(ApiScanClientId);TenantId=$(ApiScanTenant);AppKey=$(ApiScanSecret)
|
||||
|
||||
- task: SdtReport@2
|
||||
displayName: Create Security Analysis Report
|
||||
displayName: 📃 Create Security Analysis Report
|
||||
inputs:
|
||||
GdnExportAllTools: true
|
||||
|
||||
- task: PublishSecurityAnalysisLogs@3
|
||||
displayName: Publish Code Analysis Logs
|
||||
displayName: 📢 Publish Code Analysis Logs
|
||||
inputs:
|
||||
ArtifactName: CodeAnalysisLogs
|
||||
ArtifactType: Container
|
||||
|
@ -59,7 +62,7 @@ steps:
|
|||
ToolLogsNotFoundAction: Standard
|
||||
|
||||
- task: PostAnalysis@2
|
||||
displayName: Break on compliance issues
|
||||
displayName: 🏋️♀️ Break on compliance issues
|
||||
inputs:
|
||||
GdnBreakAllTools: true
|
||||
GdnBreakGdnToolBinSkimSeverity: Warning
|
||||
|
@ -71,5 +74,5 @@ steps:
|
|||
# This is useful when false positives appear so we can copy some of the output into the suppressions file.
|
||||
- publish: $(Build.ArtifactStagingDirectory)/guardian_failures_as_suppressions
|
||||
artifact: guardian_failures_as_suppressions
|
||||
displayName: Publish Guardian failures
|
||||
displayName: 🔍 Publish Guardian failures
|
||||
condition: failed()
|
||||
|
|
|
@ -0,0 +1,44 @@
|
|||
<RunSettings>
|
||||
<DataCollectionRunSettings>
|
||||
<DataCollectors>
|
||||
<DataCollector friendlyName="Code Coverage" uri="datacollector://Microsoft/CodeCoverage/2.0" assemblyQualifiedName="Microsoft.VisualStudio.Coverage.DynamicCoverageDataCollector, Microsoft.VisualStudio.TraceCollector, Version=11.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<Configuration>
|
||||
<CodeCoverage>
|
||||
<ModulePaths>
|
||||
<Include>
|
||||
<ModulePath>\.dll$</ModulePath>
|
||||
<ModulePath>\.exe$</ModulePath>
|
||||
</Include>
|
||||
<Exclude>
|
||||
<ModulePath>xunit\..*</ModulePath>
|
||||
</Exclude>
|
||||
</ModulePaths>
|
||||
<Attributes>
|
||||
<Exclude>
|
||||
<Attribute>^System\.Diagnostics\.DebuggerHiddenAttribute$</Attribute>
|
||||
<Attribute>^System\.Diagnostics\.DebuggerNonUserCodeAttribute$</Attribute>
|
||||
<Attribute>^System\.CodeDom\.Compiler\.GeneratedCodeAttribute$</Attribute>
|
||||
<Attribute>^System\.Diagnostics\.CodeAnalysis\.ExcludeFromCodeCoverageAttribute$</Attribute>
|
||||
</Exclude>
|
||||
</Attributes>
|
||||
<!-- We recommend you do not change the following values: -->
|
||||
<!-- Set this to True to collect coverage information for functions marked with the "SecuritySafeCritical" attribute. Instead of writing directly into a memory location from such functions, code coverage inserts a probe that redirects to another function, which in turns writes into memory. -->
|
||||
<UseVerifiableInstrumentation>True</UseVerifiableInstrumentation>
|
||||
<!-- When set to True, collects coverage information from child processes that are launched with low-level ACLs, for example, UWP apps. -->
|
||||
<AllowLowIntegrityProcesses>True</AllowLowIntegrityProcesses>
|
||||
<!-- When set to True, collects coverage information from child processes that are launched by test or production code. -->
|
||||
<CollectFromChildProcesses>True</CollectFromChildProcesses>
|
||||
<!-- When set to True, restarts the IIS process and collects coverage information from it. -->
|
||||
<CollectAspDotNet>False</CollectAspDotNet>
|
||||
<!-- When set to True, static native instrumentation will be enabled. -->
|
||||
<EnableStaticNativeInstrumentation>True</EnableStaticNativeInstrumentation>
|
||||
<!-- When set to True, dynamic native instrumentation will be enabled. -->
|
||||
<EnableDynamicNativeInstrumentation>True</EnableDynamicNativeInstrumentation>
|
||||
<!-- When set to True, instrumented binaries on disk are removed and original files are restored. -->
|
||||
<EnableStaticNativeInstrumentationRestore>True</EnableStaticNativeInstrumentationRestore>
|
||||
</CodeCoverage>
|
||||
</Configuration>
|
||||
</DataCollector>
|
||||
</DataCollectors>
|
||||
</DataCollectionRunSettings>
|
||||
</RunSettings>
|
|
@ -0,0 +1 @@
|
|||
'Visual Studio - VS Core'
|
|
@ -1,4 +1,4 @@
|
|||
$InsertedPkgs = (& "$PSScriptRoot\..\artifacts\VSInsertion.ps1" -SbomNotRequired)
|
||||
$InsertedPkgs = (& "$PSScriptRoot\..\artifacts\VSInsertion.ps1")
|
||||
|
||||
$icv=@()
|
||||
foreach ($kvp in $InsertedPkgs.GetEnumerator()) {
|
||||
|
|
|
@ -1 +1,13 @@
|
|||
'Andrew Arnott'
|
||||
# This is a list of AzDO account names or email addresses.
|
||||
# Add your team DL and/or whoever should be notified of insertion PRs.
|
||||
$contacts = ,$env:BUILD_REQUESTEDFOREMAIL
|
||||
$contacts += 'Andrew Arnott'
|
||||
|
||||
if (Test-Path "$PSScriptRoot\TeamEmail.ps1") {
|
||||
$contacts += & "$PSScriptRoot\TeamEmail.ps1"
|
||||
}
|
||||
|
||||
$contacts = $contacts |? { $_ }
|
||||
if ($contacts) {
|
||||
[string]::Join(',', $contacts)
|
||||
}
|
||||
|
|
|
@ -1,7 +1,14 @@
|
|||
#!/usr/bin/env pwsh
|
||||
|
||||
# This script returns a hashtable of build variables that should be set
|
||||
# at the start of a build or release definition's execution.
|
||||
<#
|
||||
.SYNOPSIS
|
||||
This script returns a hashtable of build variables that should be set
|
||||
at the start of a build or release definition's execution.
|
||||
#>
|
||||
|
||||
[CmdletBinding(SupportsShouldProcess = $true)]
|
||||
param (
|
||||
)
|
||||
|
||||
$vars = @{}
|
||||
|
||||
|
|
|
@ -1,13 +1,20 @@
|
|||
# This script translates the variables returned by the _all.ps1 script
|
||||
# into commands that instruct Azure Pipelines to actually set those variables for other pipeline tasks to consume.
|
||||
<#
|
||||
.SYNOPSIS
|
||||
This script translates the variables returned by the _all.ps1 script
|
||||
into commands that instruct Azure Pipelines to actually set those variables for other pipeline tasks to consume.
|
||||
|
||||
# The build or release definition may have set these variables to override
|
||||
# what the build would do. So only set them if they have not already been set.
|
||||
The build or release definition may have set these variables to override
|
||||
what the build would do. So only set them if they have not already been set.
|
||||
#>
|
||||
|
||||
[CmdletBinding()]
|
||||
param (
|
||||
)
|
||||
|
||||
(& "$PSScriptRoot\_all.ps1").GetEnumerator() |% {
|
||||
# Always use ALL CAPS for env var names since Azure Pipelines converts variable names to all caps and on non-Windows OS, env vars are case sensitive.
|
||||
$keyCaps = $_.Key.ToUpper()
|
||||
if (Test-Path -Path "env:$keyCaps") {
|
||||
if ((Test-Path "env:$keyCaps") -and (Get-Content "env:$keyCaps")) {
|
||||
Write-Host "Skipping setting $keyCaps because variable is already set to '$(Get-Content env:$keyCaps)'." -ForegroundColor Cyan
|
||||
} else {
|
||||
Write-Host "$keyCaps=$($_.Value)" -ForegroundColor Yellow
|
||||
|
|
|
@ -20,15 +20,15 @@ jobs:
|
|||
- checkout: none
|
||||
- powershell: Write-Host "##vso[build.updatebuildnumber]$(resources.pipeline.CI.runName)"
|
||||
displayName: Set pipeline name
|
||||
- task: NuGetAuthenticate@0
|
||||
displayName: Authenticate NuGet feeds
|
||||
inputs:
|
||||
forceReinstallCredentialProvider: true
|
||||
- task: UseDotNet@2
|
||||
displayName: Install .NET SDK
|
||||
inputs:
|
||||
packageType: sdk
|
||||
version: 6.x
|
||||
- task: NuGetAuthenticate@1
|
||||
displayName: Authenticate NuGet feeds
|
||||
inputs:
|
||||
forceReinstallCredentialProvider: true
|
||||
- template: release-deployment-prep.yml
|
||||
- download: CI
|
||||
artifact: VSInsertion-Windows
|
||||
|
|
|
@ -0,0 +1,84 @@
|
|||
# This is a top-level pipeline file, which is designed to be added as an optional PR build policy
|
||||
# so that a VS insertion and all the validation that entails can be done before ever merging the PR
|
||||
# in its original repo.
|
||||
|
||||
trigger: none # We only want to trigger manually or based on resources
|
||||
pr: none
|
||||
|
||||
stages:
|
||||
- stage: Build
|
||||
variables:
|
||||
DOTNET_SKIP_FIRST_TIME_EXPERIENCE: true
|
||||
NUGET_PACKAGES: $(Agent.TempDirectory)/.nuget/packages
|
||||
SignTypeSelection: Real
|
||||
BuildConfiguration: Release
|
||||
ValidationBuild: true
|
||||
|
||||
jobs:
|
||||
- template: build.yml
|
||||
parameters:
|
||||
EnableCompliance: false
|
||||
EnableAPIScan: false
|
||||
windowsPool: VSEngSS-MicroBuild2022-1ES
|
||||
includeMacOS: false
|
||||
RunTests: false
|
||||
|
||||
- template: prepare-insertion-stages.yml
|
||||
|
||||
- stage: insertion
|
||||
displayName: VS insertion
|
||||
jobs:
|
||||
- job: insertion
|
||||
displayName: VS insertion
|
||||
pool: VSEngSS-MicroBuild2022-1ES
|
||||
steps:
|
||||
- checkout: self
|
||||
clean: true
|
||||
fetchDepth: 1
|
||||
- task: UseDotNet@2
|
||||
displayName: Install .NET SDK
|
||||
inputs:
|
||||
packageType: sdk
|
||||
version: 6.x
|
||||
- task: NuGetAuthenticate@1
|
||||
displayName: Authenticate NuGet feeds
|
||||
inputs:
|
||||
forceReinstallCredentialProvider: true
|
||||
- download: current
|
||||
artifact: Variables-Windows
|
||||
displayName: Download Variables-Windows artifact
|
||||
- task: PowerShell@2
|
||||
displayName: Set pipeline variables based on artifacts
|
||||
inputs:
|
||||
targetType: filePath
|
||||
filePath: $(Pipeline.Workspace)/Variables-Windows/_pipelines.ps1
|
||||
- download: current
|
||||
artifact: VSInsertion-Windows
|
||||
displayName: Download VSInsertion-Windows artifact
|
||||
- script: dotnet nuget push VSInsertion-windows\*.nupkg -s https://pkgs.dev.azure.com/devdiv/_packaging/VS/nuget/v3/index.json -k azdo --skip-duplicate
|
||||
displayName: Push CoreXT packages to VS feed
|
||||
workingDirectory: $(Pipeline.Workspace)
|
||||
- task: MicroBuildInsertVsPayload@4
|
||||
displayName: Insert VS Payload
|
||||
inputs:
|
||||
TeamName: $(TeamName)
|
||||
TeamEmail: $(TeamEmail)
|
||||
InsertionPayloadName: $(Build.Repository.Name) VALIDATION BUILD $(Build.BuildNumber) ($(Build.SourceBranch))
|
||||
InsertionDescription: |
|
||||
This PR is for **validation purposes only** for !$(System.PullRequest.PullRequestId). **Do not complete**.
|
||||
CustomScriptExecutionCommand: src/VSSDK/NuGet/AllowUnstablePackages.ps1
|
||||
InsertionBuildPolicy: Request Perf DDRITs
|
||||
InsertionReviewers: $(Build.RequestedForEmail)
|
||||
AutoCompletePR: false
|
||||
- powershell: |
|
||||
$insertionPRId = azure-pipelines/Get-InsertionPRId.ps1
|
||||
$Markdown = @"
|
||||
Validation insertion pull request created: !$insertionPRId
|
||||
Please check status there before proceeding to merge this PR.
|
||||
Remember to Abandon and (if allowed) to Delete Source Branch on that insertion PR when validation is complete.
|
||||
"@
|
||||
azure-pipelines/PostPRMessage.ps1 -AccessToken '$(System.AccessToken)' -Markdown $Markdown -Verbose
|
||||
displayName: Comment on pull request
|
||||
condition: and(succeeded(), eq(variables['Build.Reason'], 'PullRequest'))
|
||||
- task: MicroBuildCleanup@1
|
||||
displayName: Send Telemetry
|
|
@ -1,6 +1,6 @@
|
|||
{
|
||||
"sdk": {
|
||||
"version": "6.0.200",
|
||||
"version": "7.0.100-rc.2.22477.23",
|
||||
"rollForward": "patch",
|
||||
"allowPrerelease": false
|
||||
}
|
||||
|
|
12
init.ps1
12
init.ps1
|
@ -35,6 +35,8 @@
|
|||
The environment is configured to build pseudo-loc for JPN only, but may be used to build
|
||||
all languages with shipping-style loc by using the `/p:loctype=full,loclanguages=vs`
|
||||
when building.
|
||||
.PARAMETER Sbom
|
||||
Install the MicroBuild SBOM plugin.
|
||||
.PARAMETER AccessToken
|
||||
An optional access token for authenticating to Azure Artifacts authenticated feeds.
|
||||
#>
|
||||
|
@ -55,6 +57,8 @@ Param (
|
|||
[Parameter()]
|
||||
[switch]$Localization,
|
||||
[Parameter()]
|
||||
[switch]$SBOM,
|
||||
[Parameter()]
|
||||
[string]$AccessToken
|
||||
)
|
||||
|
||||
|
@ -111,6 +115,14 @@ try {
|
|||
$EnvVars['LocLanguages'] = "JPN"
|
||||
}
|
||||
|
||||
if ($SBOM) {
|
||||
Write-Host "Installing MicroBuild SBOM plugin" -ForegroundColor $HeaderColor
|
||||
& $InstallNuGetPkgScriptPath MicroBuild.Plugins.Sbom -source $MicroBuildPackageSource -Verbosity $nugetVerbosity
|
||||
$PkgMicrosoft_ManifestTool_CrossPlatform = & $InstallNuGetPkgScriptPath Microsoft.ManifestTool.CrossPlatform -source 'https://1essharedassets.pkgs.visualstudio.com/1esPkgs/_packaging/SBOMTool/nuget/v3/index.json' -Verbosity $nugetVerbosity
|
||||
$EnvVars['GenerateSBOM'] = "true"
|
||||
$EnvVars['PkgMicrosoft_ManifestTool_CrossPlatform'] = $PkgMicrosoft_ManifestTool_CrossPlatform
|
||||
}
|
||||
|
||||
& "$PSScriptRoot/tools/Set-EnvVars.ps1" -Variables $EnvVars -PrependPath $PrependPath | Out-Null
|
||||
}
|
||||
catch {
|
||||
|
|
16
nuget.config
16
nuget.config
|
@ -2,22 +2,14 @@
|
|||
<configuration>
|
||||
<config>
|
||||
<add key="repositorypath" value="packages" />
|
||||
<add key="signatureValidationMode" value="require" />
|
||||
</config>
|
||||
<packageSources>
|
||||
<!--To inherit the global NuGet package sources remove the <clear/> line below -->
|
||||
<clear />
|
||||
<add key="msft_consumption" value="https://pkgs.dev.azure.com/azure-public/vside/_packaging/msft_consumption/nuget/v3/index.json" />
|
||||
</packageSources>
|
||||
<trustedSigners>
|
||||
<repository name="nuget" serviceIndex="https://api.nuget.org/v3/index.json">
|
||||
<owners>Microsoft;xunit;manuel.roemer;sharwell;jamesnk;aarnott;MarcoRossignoli;Thecentury;kzu;castleproject</owners>
|
||||
<certificate fingerprint="0e5f38f57dc1bcc806d8494f4f90fbcedd988b46760709cbeec6f4219aa6157d" hashAlgorithm="SHA256" allowUntrustedRoot="false" />
|
||||
<certificate fingerprint="5a2901d6ada3d18260b9c6dfe2133c95d74b9eef6ae0e5dc334c8454d1477df4" hashAlgorithm="SHA256" allowUntrustedRoot="false" />
|
||||
</repository>
|
||||
<author name="Microsoft">
|
||||
<certificate fingerprint="aa12da22a49bce7d5c1ae64cc1f3d892f150da76140f210abd2cbffca2c18a27" hashAlgorithm="SHA256" allowUntrustedRoot="false" />
|
||||
<certificate fingerprint="3f9001ea83c560d712c24cf213c3d312cb3bff51ee89435d3430bd06b5d0eece" hashAlgorithm="SHA256" allowUntrustedRoot="false" />
|
||||
</author>
|
||||
</trustedSigners>
|
||||
<disabledPackageSources>
|
||||
<!-- Defend against user or machine level disabling of sources that we list in this file. -->
|
||||
<clear />
|
||||
</disabledPackageSources>
|
||||
</configuration>
|
||||
|
|
|
@ -23,7 +23,4 @@
|
|||
<DependentUpon>Strings.resx</DependentUpon>
|
||||
</Compile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.CodeAnalysis.FxCopAnalyzers" Version="3.3.1" PrivateAssets="all" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
|
@ -10,6 +10,9 @@
|
|||
},
|
||||
"fileNamingConvention": "stylecop",
|
||||
"xmlHeader": false
|
||||
},
|
||||
"orderingRules": {
|
||||
"usingDirectivesPlacement": "outsideNamespace"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -50,3 +50,6 @@ dotnet_diagnostic.CA2007.severity = none
|
|||
|
||||
# SA1401: Fields should be private
|
||||
dotnet_diagnostic.SA1401.severity = silent
|
||||
|
||||
# SA1133: Do not combine attributes
|
||||
dotnet_diagnostic.SA1133.severity = silent
|
||||
|
|
|
@ -5,8 +5,4 @@
|
|||
<IsPackable>false</IsPackable>
|
||||
<CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.VisualStudio.Internal.MicroBuild.NonShipping" Version="$(MicroBuildVersion)" PrivateAssets="all" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
|
@ -1,10 +1,3 @@
|
|||
<Project>
|
||||
<PropertyGroup Condition=" '$(IsTestProject)' == 'true' ">
|
||||
<CoverletOutputFormat>cobertura</CoverletOutputFormat>
|
||||
<Exclude>[xunit.*]*</Exclude>
|
||||
<!-- Ensure we preserve each coverlet output file per target framework: https://github.com/tonerdo/coverlet/issues/177 -->
|
||||
<CoverletOutput>$(OutputPath)/</CoverletOutput>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory)../, Directory.Build.targets))\Directory.Build.targets" Condition=" '$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory)../, Directory.Build.targets))' != '' " />
|
||||
</Project>
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
<Project>
|
||||
<Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory)../, Directory.Packages.props))\Directory.Packages.props" Condition=" '$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory)../, Directory.Packages.props))' != '' " />
|
||||
|
||||
<ItemGroup>
|
||||
<GlobalPackageReference Include="Microsoft.VisualStudio.Internal.MicroBuild.NonShipping" Version="$(MicroBuildVersion)" />
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -1,13 +1,12 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net472;netcoreapp3.1;net5.0</TargetFrameworks>
|
||||
<TargetFrameworks>net472;netcoreapp3.1;net6.0</TargetFrameworks>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Moq" Version="4.18.1" />
|
||||
<PackageReference Include="xunit" Version="2.4.1" />
|
||||
<PackageReference Include="xunit.runner.visualstudio" Version="2.4.5" />
|
||||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
|
||||
<PackageReference Include="coverlet.msbuild" Version="3.1.2" />
|
||||
<PackageReference Include="Microsoft.NET.Test.Sdk" />
|
||||
<PackageReference Include="Moq" />
|
||||
<PackageReference Include="xunit.runner.visualstudio" />
|
||||
<PackageReference Include="xunit" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\src\Microsoft.VisualStudio.Validation\Microsoft.VisualStudio.Validation.csproj" />
|
||||
|
|
|
@ -15,20 +15,28 @@
|
|||
When using 'repo', environment variables are set to cause the locally installed dotnet SDK to be used.
|
||||
Per-repo can lead to file locking issues when dotnet.exe is left running as a build server and can be mitigated by running `dotnet build-server shutdown`.
|
||||
Per-machine requires elevation and will download and install all SDKs and runtimes to machine-wide locations so all applications can find it.
|
||||
.PARAMETER IncludeX86
|
||||
Installs a x86 SDK and runtimes in addition to the x64 ones. Only supported on Windows. Ignored on others.
|
||||
#>
|
||||
[CmdletBinding(SupportsShouldProcess=$true,ConfirmImpact='Medium')]
|
||||
Param (
|
||||
[ValidateSet('repo','user','machine')]
|
||||
[string]$InstallLocality='user'
|
||||
[string]$InstallLocality='user',
|
||||
[switch]$IncludeX86
|
||||
)
|
||||
|
||||
$DotNetInstallScriptRoot = "$PSScriptRoot/../obj/tools"
|
||||
if (!(Test-Path $DotNetInstallScriptRoot)) { New-Item -ItemType Directory -Path $DotNetInstallScriptRoot -WhatIf:$false | Out-Null }
|
||||
$DotNetInstallScriptRoot = Resolve-Path $DotNetInstallScriptRoot
|
||||
|
||||
# Look up actual required .NET Core SDK version from global.json
|
||||
# Look up actual required .NET SDK version from global.json
|
||||
$sdkVersion = & "$PSScriptRoot/../azure-pipelines/variables/DotNetSdkVersion.ps1"
|
||||
|
||||
If ($IncludeX86 -and ($IsMacOS -or $IsLinux)) {
|
||||
Write-Verbose "Ignoring -IncludeX86 switch because 32-bit runtimes are only supported on Windows."
|
||||
$IncludeX86 = $false
|
||||
}
|
||||
|
||||
$arch = [System.Runtime.InteropServices.RuntimeInformation]::ProcessArchitecture
|
||||
if (!$arch) { # Windows Powershell leaves this blank
|
||||
$arch = 'x64'
|
||||
|
@ -72,7 +80,7 @@ Function Get-FileFromWeb([Uri]$Uri, $OutDir) {
|
|||
$OutFile = Join-Path $OutDir $Uri.Segments[-1]
|
||||
if (!(Test-Path $OutFile)) {
|
||||
Write-Verbose "Downloading $Uri..."
|
||||
if (!(Test-Path $OutDir)) { mkdir $OutDir }
|
||||
if (!(Test-Path $OutDir)) { New-Item -ItemType Directory -Path $OutDir | Out-Null }
|
||||
try {
|
||||
(New-Object System.Net.WebClient).DownloadFile($Uri, $OutFile)
|
||||
} finally {
|
||||
|
@ -83,40 +91,36 @@ Function Get-FileFromWeb([Uri]$Uri, $OutDir) {
|
|||
$OutFile
|
||||
}
|
||||
|
||||
Function Get-InstallerExe($Version, [switch]$Runtime) {
|
||||
$sdkOrRuntime = 'Sdk'
|
||||
if ($Runtime) { $sdkOrRuntime = 'Runtime' }
|
||||
|
||||
Function Get-InstallerExe(
|
||||
$Version,
|
||||
$Architecture,
|
||||
[ValidateSet('Sdk','Runtime','WindowsDesktop')]
|
||||
[string]$sku
|
||||
) {
|
||||
# Get the latest/actual version for the specified one
|
||||
$TypedVersion = [Version]$Version
|
||||
if ($TypedVersion.Build -eq -1) {
|
||||
$versionInfo = -Split (Invoke-WebRequest -Uri "https://dotnetcli.blob.core.windows.net/dotnet/$sdkOrRuntime/$Version/latest.version" -UseBasicParsing)
|
||||
$versionInfo = -Split (Invoke-WebRequest -Uri "https://dotnetcli.blob.core.windows.net/dotnet/$sku/$Version/latest.version" -UseBasicParsing)
|
||||
$Version = $versionInfo[-1]
|
||||
}
|
||||
|
||||
$majorMinor = "$($TypedVersion.Major).$($TypedVersion.Minor)"
|
||||
$ReleasesFile = Join-Path $DotNetInstallScriptRoot "$majorMinor\releases.json"
|
||||
if (!(Test-Path $ReleasesFile)) {
|
||||
Get-FileFromWeb -Uri "https://dotnetcli.blob.core.windows.net/dotnet/release-metadata/$majorMinor/releases.json" -OutDir (Split-Path $ReleasesFile)
|
||||
Get-FileFromWeb -Uri "https://dotnetcli.blob.core.windows.net/dotnet/release-metadata/$majorMinor/releases.json" -OutDir (Split-Path $ReleasesFile) | Out-Null
|
||||
}
|
||||
|
||||
$releases = Get-Content $ReleasesFile | ConvertFrom-Json
|
||||
$url = $null
|
||||
foreach ($release in $releases.releases) {
|
||||
$filesElement = $null
|
||||
if ($Runtime) {
|
||||
if ($release.runtime.version -eq $Version) {
|
||||
$filesElement = $release.runtime.files
|
||||
}
|
||||
} else {
|
||||
if ($release.sdk.version -eq $Version) {
|
||||
$filesElement = $release.sdk.files
|
||||
}
|
||||
if ($release.$sku.version -eq $Version) {
|
||||
$filesElement = $release.$sku.files
|
||||
}
|
||||
|
||||
if ($filesElement) {
|
||||
foreach ($file in $filesElement) {
|
||||
if ($file.rid -eq "win-$arch") {
|
||||
if ($file.rid -eq "win-$Architecture") {
|
||||
$url = $file.url
|
||||
Break
|
||||
}
|
||||
|
@ -131,26 +135,23 @@ Function Get-InstallerExe($Version, [switch]$Runtime) {
|
|||
if ($url) {
|
||||
Get-FileFromWeb -Uri $url -OutDir $DotNetInstallScriptRoot
|
||||
} else {
|
||||
Write-Error "Unable to find release of $sdkOrRuntime v$Version"
|
||||
Write-Error "Unable to find release of $sku v$Version"
|
||||
}
|
||||
}
|
||||
|
||||
Function Install-DotNet($Version, [switch]$Runtime) {
|
||||
if ($Runtime) { $sdkSubstring = '' } else { $sdkSubstring = 'SDK ' }
|
||||
Write-Host "Downloading .NET Core $sdkSubstring$Version..."
|
||||
$Installer = Get-InstallerExe -Version $Version -Runtime:$Runtime
|
||||
Write-Host "Installing .NET Core $sdkSubstring$Version..."
|
||||
Function Install-DotNet($Version, $Architecture, [ValidateSet('Sdk','Runtime','WindowsDesktop')][string]$sku = 'Sdk') {
|
||||
Write-Host "Downloading .NET Core $sku $Version..."
|
||||
$Installer = Get-InstallerExe -Version $Version -Architecture $Architecture -sku $sku
|
||||
Write-Host "Installing .NET Core $sku $Version..."
|
||||
cmd /c start /wait $Installer /install /passive /norestart
|
||||
if ($LASTEXITCODE -eq 3010) {
|
||||
Write-Verbose "Restart required"
|
||||
} elseif ($LASTEXITCODE -ne 0) {
|
||||
throw "Failure to install .NET Core SDK"
|
||||
throw "Failure to install .NET SDK"
|
||||
}
|
||||
}
|
||||
|
||||
$switches = @(
|
||||
'-Architecture',$arch
|
||||
)
|
||||
$switches = @()
|
||||
$envVars = @{
|
||||
# For locally installed dotnet, skip first time experience which takes a long time
|
||||
'DOTNET_SKIP_FIRST_TIME_EXPERIENCE' = 'true';
|
||||
|
@ -161,15 +162,37 @@ if ($InstallLocality -eq 'machine') {
|
|||
$DotNetInstallDir = '/usr/share/dotnet'
|
||||
} else {
|
||||
$restartRequired = $false
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core SDK $sdkVersion", "Install")) {
|
||||
Install-DotNet -Version $sdkVersion
|
||||
if ($PSCmdlet.ShouldProcess(".NET SDK $sdkVersion", "Install")) {
|
||||
Install-DotNet -Version $sdkVersion -Architecture $arch
|
||||
$restartRequired = $restartRequired -or ($LASTEXITCODE -eq 3010)
|
||||
|
||||
if ($IncludeX86) {
|
||||
Install-DotNet -Version $sdkVersion -Architecture x86
|
||||
$restartRequired = $restartRequired -or ($LASTEXITCODE -eq 3010)
|
||||
}
|
||||
}
|
||||
|
||||
$runtimeVersions | Get-Unique |% {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core runtime $_", "Install")) {
|
||||
Install-DotNet -Version $_ -Runtime
|
||||
$runtimeVersions | Sort-Object | Get-Unique |% {
|
||||
if ($PSCmdlet.ShouldProcess(".NET runtime $_", "Install")) {
|
||||
Install-DotNet -Version $_ -sku Runtime -Architecture $arch
|
||||
$restartRequired = $restartRequired -or ($LASTEXITCODE -eq 3010)
|
||||
|
||||
if ($IncludeX86) {
|
||||
Install-DotNet -Version $_ -sku Runtime -Architecture x86
|
||||
$restartRequired = $restartRequired -or ($LASTEXITCODE -eq 3010)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$windowsDesktopRuntimeVersions | Sort-Object | Get-Unique |% {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Windows Desktop $_", "Install")) {
|
||||
Install-DotNet -Version $_ -sku WindowsDesktop -Architecture $arch
|
||||
$restartRequired = $restartRequired -or ($LASTEXITCODE -eq 3010)
|
||||
|
||||
if ($IncludeX86) {
|
||||
Install-DotNet -Version $_ -sku WindowsDesktop -Architecture x86
|
||||
$restartRequired = $restartRequired -or ($LASTEXITCODE -eq 3010)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -182,20 +205,34 @@ if ($InstallLocality -eq 'machine') {
|
|||
}
|
||||
} elseif ($InstallLocality -eq 'repo') {
|
||||
$DotNetInstallDir = "$DotNetInstallScriptRoot/.dotnet"
|
||||
$DotNetX86InstallDir = "$DotNetInstallScriptRoot/x86/.dotnet"
|
||||
} elseif ($env:AGENT_TOOLSDIRECTORY) {
|
||||
$DotNetInstallDir = "$env:AGENT_TOOLSDIRECTORY/dotnet"
|
||||
$DotNetX86InstallDir = "$env:AGENT_TOOLSDIRECTORY/x86/dotnet"
|
||||
} else {
|
||||
$DotNetInstallDir = Join-Path $HOME .dotnet
|
||||
}
|
||||
|
||||
Write-Host "Installing .NET Core SDK and runtimes to $DotNetInstallDir" -ForegroundColor Blue
|
||||
|
||||
if ($DotNetInstallDir) {
|
||||
$switches += '-InstallDir',"`"$DotNetInstallDir`""
|
||||
if (!(Test-Path $DotNetInstallDir)) { New-Item -ItemType Directory -Path $DotNetInstallDir }
|
||||
$DotNetInstallDir = Resolve-Path $DotNetInstallDir
|
||||
Write-Host "Installing .NET SDK and runtimes to $DotNetInstallDir" -ForegroundColor Blue
|
||||
$envVars['DOTNET_MULTILEVEL_LOOKUP'] = '0'
|
||||
$envVars['DOTNET_ROOT'] = $DotNetInstallDir
|
||||
}
|
||||
|
||||
if ($IncludeX86) {
|
||||
if ($DotNetX86InstallDir) {
|
||||
if (!(Test-Path $DotNetX86InstallDir)) { New-Item -ItemType Directory -Path $DotNetX86InstallDir }
|
||||
$DotNetX86InstallDir = Resolve-Path $DotNetX86InstallDir
|
||||
Write-Host "Installing x86 .NET SDK and runtimes to $DotNetX86InstallDir" -ForegroundColor Blue
|
||||
} else {
|
||||
# Only machine-wide or repo-wide installations can handle two unique dotnet.exe architectures.
|
||||
Write-Error "The installation location or OS isn't supported for x86 installation. Try a different -InstallLocality value."
|
||||
return 1
|
||||
}
|
||||
}
|
||||
|
||||
if ($IsMacOS -or $IsLinux) {
|
||||
$DownloadUri = "https://raw.githubusercontent.com/dotnet/install-scripts/781752509a890ca7520f1182e8bae71f9a53d754/src/dotnet-install.sh"
|
||||
$DotNetInstallScriptPath = "$DotNetInstallScriptRoot/dotnet-install.sh"
|
||||
|
@ -219,47 +256,89 @@ $DotNetInstallScriptPathExpression = "& '$DotNetInstallScriptPathExpression'"
|
|||
$anythingInstalled = $false
|
||||
$global:LASTEXITCODE = 0
|
||||
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core SDK $sdkVersion", "Install")) {
|
||||
if ($PSCmdlet.ShouldProcess(".NET SDK $sdkVersion", "Install")) {
|
||||
$anythingInstalled = $true
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Version $sdkVersion $switches"
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Version $sdkVersion -Architecture $arch -InstallDir $DotNetInstallDir $switches"
|
||||
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Error ".NET SDK installation failure: $LASTEXITCODE"
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
} else {
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Version $sdkVersion $switches -DryRun"
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Version $sdkVersion -Architecture $arch -InstallDir $DotNetInstallDir $switches -DryRun"
|
||||
}
|
||||
|
||||
if ($IncludeX86) {
|
||||
if ($PSCmdlet.ShouldProcess(".NET x86 SDK $sdkVersion", "Install")) {
|
||||
$anythingInstalled = $true
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Version $sdkVersion -Architecture x86 -InstallDir $DotNetX86InstallDir $switches"
|
||||
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Error ".NET x86 SDK installation failure: $LASTEXITCODE"
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
} else {
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Version $sdkVersion -Architecture x86 -InstallDir $DotNetX86InstallDir $switches -DryRun"
|
||||
}
|
||||
}
|
||||
|
||||
$dotnetRuntimeSwitches = $switches + '-Runtime','dotnet'
|
||||
|
||||
$runtimeVersions | Sort-Object -Unique |% {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core runtime $_", "Install")) {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core $Arch runtime $_", "Install")) {
|
||||
$anythingInstalled = $true
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ $dotnetRuntimeSwitches"
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture $arch -InstallDir $DotNetInstallDir $dotnetRuntimeSwitches"
|
||||
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Error ".NET SDK installation failure: $LASTEXITCODE"
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
} else {
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ $dotnetRuntimeSwitches -DryRun"
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture $arch -InstallDir $DotNetInstallDir $dotnetRuntimeSwitches -DryRun"
|
||||
}
|
||||
|
||||
if ($IncludeX86) {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core x86 runtime $_", "Install")) {
|
||||
$anythingInstalled = $true
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture x86 -InstallDir $DotNetX86InstallDir $dotnetRuntimeSwitches"
|
||||
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Error ".NET SDK installation failure: $LASTEXITCODE"
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
} else {
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture x86 -InstallDir $DotNetX86InstallDir $dotnetRuntimeSwitches -DryRun"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$windowsDesktopRuntimeSwitches = $switches + '-Runtime','windowsdesktop'
|
||||
|
||||
$windowsDesktopRuntimeVersions | Sort-Object -Unique |% {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core WindowsDesktop runtime $_", "Install")) {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core WindowsDesktop $arch runtime $_", "Install")) {
|
||||
$anythingInstalled = $true
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ $windowsDesktopRuntimeSwitches"
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture $arch -InstallDir $DotNetInstallDir $windowsDesktopRuntimeSwitches"
|
||||
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Error ".NET SDK installation failure: $LASTEXITCODE"
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
} else {
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ $windowsDesktopRuntimeSwitches -DryRun"
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture $arch -InstallDir $DotNetInstallDir $windowsDesktopRuntimeSwitches -DryRun"
|
||||
}
|
||||
|
||||
if ($IncludeX86) {
|
||||
if ($PSCmdlet.ShouldProcess(".NET Core WindowsDesktop x86 runtime $_", "Install")) {
|
||||
$anythingInstalled = $true
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture x86 -InstallDir $DotNetX86InstallDir $windowsDesktopRuntimeSwitches"
|
||||
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Error ".NET SDK installation failure: $LASTEXITCODE"
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
} else {
|
||||
Invoke-Expression -Command "$DotNetInstallScriptPathExpression -Channel $_ -Architecture x86 -InstallDir $DotNetX86InstallDir $windowsDesktopRuntimeSwitches -DryRun"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -33,7 +33,7 @@ if ($IsMacOS -or $IsLinux) {
|
|||
|
||||
$installerScript = Join-Path $toolsPath $installerScript
|
||||
|
||||
if (!(Test-Path $installerScript)) {
|
||||
if (!(Test-Path $installerScript) -or $Force) {
|
||||
Invoke-WebRequest $sourceUrl -OutFile $installerScript
|
||||
}
|
||||
|
||||
|
@ -43,7 +43,7 @@ if ($IsMacOS -or $IsLinux) {
|
|||
chmod u+x $installerScript
|
||||
}
|
||||
|
||||
& $installerScript -Force:$Force
|
||||
& $installerScript -Force:$Force -AddNetfx -InstallNet6
|
||||
|
||||
if ($AccessToken) {
|
||||
$endpoints = @()
|
||||
|
|
Загрузка…
Ссылка в новой задаче