Create and publish VerticalAssetManifest (#19062)
Co-authored-by: Matt Mitchell <mmitche@microsoft.com> Co-authored-by: Viktor Hofer <viktor.hofer@microsoft.com>
This commit is contained in:
parent
a2f8bbc1f9
commit
ca9773f69a
6 changed files with 183 additions and 0 deletions
|
@ -441,3 +441,24 @@ jobs:
|
|||
mergeTestResults: true
|
||||
publishRunAttachments: true
|
||||
testRunTitle: SourceBuild_SmokeTests_$(Agent.JobName)
|
||||
|
||||
- task: CopyFiles@2
|
||||
inputs:
|
||||
SourceFolder: $(sourcesPath)/artifacts
|
||||
Contents: |
|
||||
VerticalManifest.xml
|
||||
assets/**
|
||||
TargetFolder: $(Build.ArtifactStagingDirectory)/publishing
|
||||
displayName: Copy artifacts to Artifact Staging Directory
|
||||
|
||||
# When building from source, the Private.SourceBuilt.Artifacts archive already contains the nuget packages
|
||||
- ${{ if ne(parameters.buildSourceOnly, 'true') }}:
|
||||
- task: CopyFiles@2
|
||||
inputs:
|
||||
SourceFolder: $(sourcesPath)/artifacts/packages
|
||||
TargetFolder: $(Build.ArtifactStagingDirectory)/publishing/packages
|
||||
displayName: Copy packages to Artifact Staging Directory
|
||||
|
||||
- publish: $(Build.ArtifactStagingDirectory)/publishing
|
||||
artifact: $(Agent.JobName)_Artifacts
|
||||
displayName: Publish Artifacts
|
||||
|
|
|
@ -206,6 +206,7 @@
|
|||
<XPlatSourceBuildTasksAssembly>$([MSBuild]::NormalizePath('$(ArtifactsBinDir)', 'Microsoft.DotNet.SourceBuild.Tasks.XPlat', '$(Configuration)', 'Microsoft.DotNet.SourceBuild.Tasks.XPlat.dll'))</XPlatSourceBuildTasksAssembly>
|
||||
<LeakDetectionTasksAssembly>$([MSBuild]::NormalizePath('$(ArtifactsBinDir)', 'Microsoft.DotNet.SourceBuild.Tasks.LeakDetection', '$(Configuration)', 'Microsoft.DotNet.SourceBuild.Tasks.LeakDetection.dll'))</LeakDetectionTasksAssembly>
|
||||
<SdkArchiveDiffTasksAssembly>$([MSBuild]::NormalizePath('$(ArtifactsBinDir)', 'Microsoft.DotNet.SourceBuild.Tasks.SdkArchiveDiff', '$(Configuration)', 'Microsoft.DotNet.SourceBuild.Tasks.SdkArchiveDiff.dll'))</SdkArchiveDiffTasksAssembly>
|
||||
<MergeAssetManifestsAssembly>$([MSBuild]::NormalizePath('$(ArtifactsBinDir)', 'Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests', '$(Configuration)', 'Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests.dll'))</MergeAssetManifestsAssembly>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(EnablePoison)' == 'true'">
|
||||
|
@ -214,6 +215,12 @@
|
|||
<PoisonedReportFile>$(PackageReportDir)poisoned.txt</PoisonedReportFile>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- The predefined environmental variable `BUILD_BUILDNUMBER` is getting overwritten in repo-projects,
|
||||
so save it in a different varialbe-->
|
||||
<PropertyGroup>
|
||||
<VmrBuildNumber>$(BUILD_BUILDNUMBER)"</VmrBuildNumber>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="$(GitInfoAllRepoPropsFile)" />
|
||||
|
||||
</Project>
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
|
||||
<Import Project="Sdk.targets" Sdk="Microsoft.NET.Sdk" />
|
||||
|
||||
<UsingTask AssemblyFile="$(MergeAssetManifestsAssembly)" TaskName="Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests" />
|
||||
|
||||
<Target Name="Build">
|
||||
<PropertyGroup>
|
||||
<BuildModeInfoText Condition="'$(DotNetBuildSourceOnly)' == 'true'">source-build</BuildModeInfoText>
|
||||
|
@ -25,6 +27,21 @@
|
|||
StopOnFirstFailure="true" />
|
||||
</Target>
|
||||
|
||||
<Target Name="MergeAssetManifests" AfterTargets="Build">
|
||||
<PropertyGroup>
|
||||
<MergedAssetManifestOutputPath>$(ArtifactsDir)VerticalManifest.xml</MergedAssetManifestOutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<RepoAssetManifest Include="$(AssetManifestsIntermediateDir)\**\*.xml" />
|
||||
</ItemGroup>
|
||||
|
||||
<Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests
|
||||
AssetManifest="@(RepoAssetManifest)"
|
||||
MergedAssetManifestOutputPath="$(MergedAssetManifestOutputPath)"
|
||||
VmrBuildNumber="$(VmrBuildNumber)" />
|
||||
</Target>
|
||||
|
||||
<Import Project="$(RepositoryEngineeringDir)build.sourcebuild.targets" Condition="'$(DotNetBuildSourceOnly)' == 'true'" />
|
||||
|
||||
<!-- Intentionally below the import to appear at the end. -->
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
BuildMSBuildSdkResolver;
|
||||
BuildSdkArchiveDiff;
|
||||
BuildLeakDetection;
|
||||
BuildMergeAssetManifests;
|
||||
ExtractToolPackage;
|
||||
GenerateRootFs;
|
||||
PoisonPrebuiltPackages" />
|
||||
|
@ -126,6 +127,24 @@
|
|||
Targets="Build" />
|
||||
</Target>
|
||||
|
||||
<Target Name="BuildMergeAssetManifests"
|
||||
DependsOnTargets="ExtractToolPackage;BuildMSBuildSdkResolver"
|
||||
Inputs="$(MSBuildProjectFullPath)"
|
||||
Outputs="$(BaseIntermediateOutputPath)MergeAssetManifests.complete">
|
||||
|
||||
<MSBuild Projects="tasks\Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests\Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests.csproj"
|
||||
Targets="Restore"
|
||||
Properties="MSBuildRestoreSessionId=$([System.Guid]::NewGuid())" />
|
||||
|
||||
<MSBuild Projects="tasks\Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests\Microsoft.DotNet.SourceBuild.Tasks.MergeAssetManifests.csproj"
|
||||
Targets="Build" />
|
||||
|
||||
<MakeDir Directories="$(BaseIntermediateOutputPath)" />
|
||||
<Touch Files="$(BaseIntermediateOutputPath)MergeAssetManifests.complete" AlwaysCreate="true">
|
||||
<Output TaskParameter="TouchedFiles" ItemName="FileWrites" />
|
||||
</Touch>
|
||||
</Target>
|
||||
|
||||
<Target Name="GenerateRootFs"
|
||||
Condition="'$(BuildOS)' != 'windows' and '$(CrossBuild)' == 'true' and '$(ROOTFS_DIR)' == ''">
|
||||
<PropertyGroup>
|
||||
|
|
|
@ -0,0 +1,103 @@
|
|||
// Licensed to the .NET Foundation under one or more agreements.
|
||||
// The .NET Foundation licenses this file to you under the MIT license.
|
||||
// See the LICENSE file in the project root for more information.
|
||||
|
||||
using Microsoft.Build.Utilities;
|
||||
using Microsoft.Build.Framework;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Xml.Linq;
|
||||
|
||||
namespace Microsoft.DotNet.SourceBuild.Tasks
|
||||
{
|
||||
public class MergeAssetManifests : Task
|
||||
{
|
||||
/// <summary>
|
||||
/// AssetManifest paths
|
||||
/// </summary>
|
||||
[Required]
|
||||
public required ITaskItem[] AssetManifest { get; init; }
|
||||
|
||||
/// <summary>
|
||||
/// Merged asset manifest output path
|
||||
/// </summary>
|
||||
[Required]
|
||||
public required string MergedAssetManifestOutputPath { get; init; }
|
||||
|
||||
/// <summary>
|
||||
/// Azure DevOps build number
|
||||
/// </summary>
|
||||
[Required]
|
||||
public required string VmrBuildNumber { get; init; }
|
||||
|
||||
private static readonly string _buildIdAttribute = "BuildId";
|
||||
private static readonly string _azureDevOpsBuildNumberAttribute = "AzureDevOpsBuildNumber";
|
||||
private static readonly string[] _ignoredAttributes = [_buildIdAttribute, _azureDevOpsBuildNumberAttribute, "IsReleaseOnlyPackageVersion"];
|
||||
|
||||
public override bool Execute()
|
||||
{
|
||||
List<XDocument> assetManifestXmls = AssetManifest.Select(xmlPath => XDocument.Load(xmlPath.ItemSpec)).ToList();
|
||||
|
||||
VerifyAssetManifests(assetManifestXmls);
|
||||
|
||||
XElement mergedManifestRoot = assetManifestXmls.First().Root
|
||||
?? throw new ArgumentException("The root element of the asset manifest is null.");
|
||||
|
||||
// Set the BuildId and AzureDevOpsBuildNumber attributes to the value of VmrBuildNumber
|
||||
mergedManifestRoot.SetAttributeValue(_buildIdAttribute, VmrBuildNumber);
|
||||
mergedManifestRoot.SetAttributeValue(_azureDevOpsBuildNumberAttribute, VmrBuildNumber);
|
||||
|
||||
List<XElement> packageElements = new();
|
||||
List<XElement> blobElements = new();
|
||||
|
||||
foreach (var assetManifestXml in assetManifestXmls)
|
||||
{
|
||||
packageElements.AddRange(assetManifestXml.Descendants("Package"));
|
||||
blobElements.AddRange(assetManifestXml.Descendants("Blob"));
|
||||
}
|
||||
|
||||
packageElements = packageElements.OrderBy(packageElement => packageElement.Attribute("Id")?.Value).ToList();
|
||||
blobElements = blobElements.OrderBy(blobElement => blobElement.Attribute("Id")?.Value).ToList();
|
||||
|
||||
XDocument verticalManifest = new(new XElement(mergedManifestRoot.Name, mergedManifestRoot.Attributes(), packageElements, blobElements));
|
||||
|
||||
File.WriteAllText(MergedAssetManifestOutputPath, verticalManifest.ToString());
|
||||
|
||||
return !Log.HasLoggedErrors;
|
||||
}
|
||||
|
||||
private static void VerifyAssetManifests(IReadOnlyList<XDocument> assetManifestXmls)
|
||||
{
|
||||
if (assetManifestXmls.Count == 0)
|
||||
{
|
||||
throw new ArgumentException("No asset manifests were provided.");
|
||||
}
|
||||
|
||||
HashSet<string> rootAttributes = assetManifestXmls
|
||||
.First()
|
||||
.Root?
|
||||
.Attributes()
|
||||
.Select(attribute => attribute.ToString())
|
||||
.ToHashSet()
|
||||
?? throw new ArgumentException("The root element of the asset manifest is null.");
|
||||
|
||||
if (assetManifestXmls.Skip(1).Any(manifest => manifest.Root?.Attributes().Count() != rootAttributes.Count))
|
||||
{
|
||||
throw new ArgumentException("The asset manifests do not have the same number of root attributes.");
|
||||
}
|
||||
|
||||
if (assetManifestXmls.Skip(1).Any(assetManifestXml =>
|
||||
!assetManifestXml.Root?.Attributes().Select(attribute => attribute.ToString())
|
||||
.All(attribute =>
|
||||
// Ignore BuildId and AzureDevOpsBuildNumber attributes, they're different for different repos,
|
||||
// TODO this should be fixed with https://github.com/dotnet/source-build/issues/3934
|
||||
_ignoredAttributes.Any(ignoredAttribute => attribute.StartsWith(ignoredAttribute)) || rootAttributes.Contains(attribute))
|
||||
?? false))
|
||||
{
|
||||
throw new ArgumentException("The asset manifests do not have the same root attributes.");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,16 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>$(NetCurrent)</TargetFramework>
|
||||
<Nullable>enable</Nullable>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Build.Utilities.Core" Version="$(MicrosoftBuildVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ReferencePath Include="@(SdkAssembly)" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
Loading…
Reference in a new issue