272 lines
18 KiB
XML
272 lines
18 KiB
XML
<!--
|
|
|
|
The targets in this file are used to implement custom <Reference> resolution.
|
|
For more details, see /docs/ReferenceResolution.md.
|
|
|
|
Properties which can be set by projects. If unset, these will be inferred.
|
|
|
|
* UseLatestPackageReferences = resolve `<Reference>` items to the latest version of PackageReferences in eng/Dependencies.props.
|
|
* UseProjectReferences = prefer project references to packages
|
|
* IsProjectReferenceProvider = when true, the assembly in this project should be available as a ProjectReferenceProvider (see below).
|
|
|
|
Items used by the resolution strategy:
|
|
|
|
* BaselinePackageReference = a list of packages that were reference in the last release of the project currently building
|
|
* LatestPackageReference = a list of the latest versions of packages
|
|
* Reference = a list of the references which are needed for compilation or runtime
|
|
* ProjectReferenceProvider = a list which maps of assembly names to the project file that produces it
|
|
-->
|
|
<Project>
|
|
|
|
<PropertyGroup>
|
|
<EnableCustomReferenceResolution Condition="'$(EnableCustomReferenceResolution)' == '' AND ('$(DotNetBuildFromSource)' != 'true' OR '$(ExcludeFromSourceBuild)' != 'true')">true</EnableCustomReferenceResolution>
|
|
|
|
<ResolveReferencesDependsOn>
|
|
ResolveCustomReferences;
|
|
$(ResolveReferencesDependsOn);
|
|
</ResolveReferencesDependsOn>
|
|
</PropertyGroup>
|
|
|
|
<PropertyGroup>
|
|
<!--
|
|
Projects should only use the latest package references when:
|
|
* preparing a new major or minor release (i.e. a non-servicing builds)
|
|
* when a project is a test or sample project
|
|
* when a package is releasing a new patch (we like to update external dependencies in patches when possible)
|
|
-->
|
|
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' AND '$(IsServicingBuild)' != 'true' ">true</UseLatestPackageReferences>
|
|
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' AND '$(IsImplementationProject)' != 'true' ">true</UseLatestPackageReferences>
|
|
<UseLatestPackageReferences
|
|
Condition=" '$(UseLatestPackageReferences)' == '' AND '$(IsImplementationProject)' == 'true' AND '$(IsPackable)' == 'true' ">true</UseLatestPackageReferences>
|
|
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' ">false</UseLatestPackageReferences>
|
|
|
|
<!--
|
|
Projects should only use the project references instead of baseline package references when:
|
|
* preparing a new major or minor release (i.e. a non-servicing builds)
|
|
* when a project is a test or sample project
|
|
We don't use project references between components in servicing builds between compontents to preserve the baseline as much as possible.
|
|
-->
|
|
<UseProjectReferences Condition=" '$(UseProjectReferences)' == '' AND '$(IsServicingBuild)' != 'true' ">true</UseProjectReferences>
|
|
<UseProjectReferences Condition=" '$(UseProjectReferences)' == '' AND '$(IsImplementationProject)' != 'true' ">true</UseProjectReferences>
|
|
<UseProjectReferences Condition=" '$(UseProjectReferences)' == '' ">false</UseProjectReferences>
|
|
|
|
<ReferenceReferenceAssemblies Condition=" '$(ReferenceReferenceAssemblies)' == '' AND '$(IsReferenceAssemblyProject)' == 'true'">true</ReferenceReferenceAssemblies>
|
|
<ReferenceReferenceAssemblies Condition=" '$(ReferenceReferenceAssemblies)' == '' ">false</ReferenceReferenceAssemblies>
|
|
|
|
<ReferenceImplementationAssemblies Condition=" '$(ReferenceImplementationAssemblies)' == '' AND '$(IsReferenceAssemblyProject)' != 'true'">true</ReferenceImplementationAssemblies>
|
|
<ReferenceImplementationAssemblies Condition=" '$(ReferenceImplementationAssemblies)' == '' ">false</ReferenceImplementationAssemblies>
|
|
</PropertyGroup>
|
|
|
|
<ItemDefinitionGroup>
|
|
<Reference>
|
|
<IsSharedSource></IsSharedSource>
|
|
</Reference>
|
|
</ItemDefinitionGroup>
|
|
|
|
<ItemGroup Condition="'$(EnableCustomReferenceResolution)' == 'true'">
|
|
<Reference Update="@(Reference)">
|
|
<IsSharedSource Condition="'%(IsSharedSource)' == '' AND $([System.String]::new('%(Identity)').EndsWith('.Sources'))">true</IsSharedSource>
|
|
</Reference>
|
|
|
|
<!-- Packages which are implicitly defined by the .NET Core SDK. -->
|
|
<_ImplicitPackageReference Include="@(PackageReference->WithMetadataValue('IsImplicitlyDefined', 'true'))" />
|
|
<!-- Capture a list of references which were set explicitly in the project. -->
|
|
<_AllowedExplicitPackageReference Include="@(PackageReference->WithMetadataValue('AllowExplicitReference', 'true'))" />
|
|
<_AllowedExplicitPackageReference Include="FSharp.Core" Condition="'$(MSBuildProjectExtension)' == '.fsproj'" />
|
|
<_ExplicitPackageReference Include="@(PackageReference)" Exclude="@(_ImplicitPackageReference);@(_AllowedExplicitPackageReference)" />
|
|
|
|
<_UnusedProjectReferenceProvider Include="@(ProjectReferenceProvider)" Exclude="@(Reference)" />
|
|
|
|
<_CompilationOnlyReference Condition="'$(TargetFramework)' == 'netstandard2.0'" Include="@(Reference->WithMetadataValue('NuGetPackageId','NETStandard.Library'))" />
|
|
|
|
<_InvalidReferenceToNonSharedFxAssembly Condition="'$(IsAspNetCoreApp)' == 'true'"
|
|
Include="@(Reference)"
|
|
Exclude="
|
|
@(AspNetCoreAppReference);
|
|
@(AspNetCoreAppReferenceAndPackage);
|
|
@(ExternalAspNetCoreAppReference);
|
|
@(_CompilationOnlyReference);
|
|
@(Reference->WithMetadataValue('IsSharedSource', 'true'))" />
|
|
<_OriginalReferences Include="@(Reference)" />
|
|
<!--
|
|
Turn Reference items into a ProjectReference when UseProjectReferences is true.
|
|
Order matters. This comes before package resolution because projects should be used when possible instead of packages.
|
|
-->
|
|
<_ProjectReferenceByAssemblyName Condition="'$(UseProjectReferences)' == 'true'"
|
|
Include="@(ProjectReferenceProvider)"
|
|
Exclude="@(_UnusedProjectReferenceProvider)" />
|
|
|
|
<!-- Use ref assembly project paths for ref assembly projects -->
|
|
<ProjectReference Condition="'$(ReferenceImplementationAssemblies)' == 'true'" Include="@(_ProjectReferenceByAssemblyName->'%(ProjectPath)')" >
|
|
<IsReferenceAssembly>false</IsReferenceAssembly>
|
|
</ProjectReference>
|
|
|
|
<ProjectReference Condition="'$(ReferenceReferenceAssemblies)' == 'true'" Include="@(_ProjectReferenceByAssemblyName->'%(RefProjectPath)')" >
|
|
<IsReferenceAssembly>true</IsReferenceAssembly>
|
|
</ProjectReference>
|
|
|
|
<Reference Remove="@(_ProjectReferenceByAssemblyName)" />
|
|
</ItemGroup>
|
|
|
|
<!--
|
|
This target resolves remaining Referene items to Packages, if possible. If not, they are left as Reference items fo the SDK to resolve.
|
|
This target helps ensure projects within the shared framework do no unintentionally add new references,
|
|
and that assemblies outside the shared framework reference the framework as a whole instead of using
|
|
individual assemblies.
|
|
-->
|
|
<Target Name="_CheckForReferenceBoundaries" BeforeTargets="CollectPackageReferences;ResolveReferences">
|
|
|
|
<Error Condition="@(_InvalidReferenceToSharedFxOnlyAssembly->Count()) != 0"
|
|
Text="Cannot reference "%(_InvalidReferenceToSharedFxOnlyAssembly.Identity)" directly because it is part of the shared framework and this project is not. Use <FrameworkReference Include="Microsoft.AspNetCore.App" /> instead." />
|
|
|
|
<Error Condition="@(_InvalidReferenceToNonSharedFxAssembly->Count()) != 0"
|
|
Text="Cannot reference "%(_InvalidReferenceToNonSharedFxAssembly.Identity)". This dependency is not in the shared framework. See docs/SharedFramework.md for instructions on how to modify what is in the shared framework." />
|
|
</Target>
|
|
|
|
<Target Name="_WarnAboutRedundantRef" AfterTargets="ResolveFrameworkReferences;ProcessFrameworkReferences">
|
|
<Warning Condition="@(FrameworkReference->WithMetadataValue('Identity', 'Microsoft.AspNetCore.App')->Count()) > 1"
|
|
Text="Redundant <FrameworkReference>. If you have an explicit item in the project file, you might be able to remove it. Some SDKs, like Microsoft.NET.Sdk.Web, add this implicitly." />
|
|
</Target>
|
|
|
|
<!--
|
|
This target resolves remaining Referene items to Packages, if possible. If not, they are left as Reference items fo the SDK to resolve.
|
|
This executes on NuGet restore and during DesignTimeBuild. It should not run in the outer, cross-targeting build.
|
|
-->
|
|
<Target Name="ResolveCustomReferences" BeforeTargets="CollectPackageReferences;ResolveAssemblyReferencesDesignTime;ResolveAssemblyReferences" Condition=" '$(TargetFramework)' != '' AND '$(EnableCustomReferenceResolution)' == 'true' ">
|
|
<ItemGroup>
|
|
<!-- Ensure only content asset are consumed from .Sources packages -->
|
|
<Reference>
|
|
<IncludeAssets Condition="'%(IsSharedSource)' == 'true'">ContentFiles;Build</IncludeAssets>
|
|
<PrivateAssets Condition="'%(IsSharedSource)' == 'true'">All</PrivateAssets>
|
|
</Reference>
|
|
|
|
<!-- Identify if any references were present in the last release of this package, but have been removed. -->
|
|
<UnusedBaselinePackageReference Include="@(BaselinePackageReference)" Exclude="@(Reference);@(_ProjectReferenceByAssemblyName);@(PackageReference)" />
|
|
<!-- Only allow suppressing baseline changes in non-servicing builds. -->
|
|
<UnusedBaselinePackageReference Remove="@(SuppressBaselineReference)" Condition="'$(IsServicingBuild)' != 'true'"/>
|
|
|
|
<!--
|
|
MSBuild does not provide a way to join on matching identities in a Condition,
|
|
but you can do a cartesian product of two item groups and filter out mismatched id's in a second pass.
|
|
-->
|
|
<_LatestPackageReferenceWithVersion Include="@(Reference)" Condition=" '$(UseLatestPackageReferences)' == 'true' ">
|
|
<Id>%(LatestPackageReference.Identity)</Id>
|
|
<Version>%(LatestPackageReference.Version)</Version>
|
|
</_LatestPackageReferenceWithVersion>
|
|
<_LatestPackageReferenceWithVersion Remove="@(_LatestPackageReferenceWithVersion)" Condition="'%(Id)' != '%(Identity)' " />
|
|
|
|
<!-- Remove reference items that have been resolved to a LatestPackageReference item. -->
|
|
<Reference Remove="@(_LatestPackageReferenceWithVersion)" />
|
|
<PackageReference Include="@(_LatestPackageReferenceWithVersion)" IsImplicitlyDefined="true" />
|
|
|
|
<!-- Resolve references from BaselinePackageReference for servicing builds. -->
|
|
<_BaselinePackageReferenceWithVersion Include="@(Reference)" Condition=" '$(IsServicingBuild)' == 'true' OR '$(UseLatestPackageReferences)' != 'true' ">
|
|
<Id>%(BaselinePackageReference.Identity)</Id>
|
|
<Version>%(BaselinePackageReference.Version)</Version>
|
|
</_BaselinePackageReferenceWithVersion>
|
|
|
|
<_BaselinePackageReferenceWithVersion Remove="@(_BaselinePackageReferenceWithVersion)" Condition="'%(Id)' != '%(Identity)' " />
|
|
|
|
<!-- Remove reference items that have been resolved to a BaselinePackageReference item. -->
|
|
<PackageReference Include="@(_BaselinePackageReferenceWithVersion)" IsImplicitlyDefined="true" />
|
|
<Reference Remove="@(_BaselinePackageReferenceWithVersion)" />
|
|
|
|
<!-- For PrivateAssets=All references, like .Sources packages, fallback to LatestPackageReferences. -->
|
|
<_PrivatePackageReferenceWithVersion Include="@(Reference->WithMetadataValue('PrivateAssets', 'All'))">
|
|
<Id>%(LatestPackageReference.Identity)</Id>
|
|
<Version>%(LatestPackageReference.Version)</Version>
|
|
</_PrivatePackageReferenceWithVersion>
|
|
|
|
<_PrivatePackageReferenceWithVersion Remove="@(_PrivatePackageReferenceWithVersion)" Condition="'%(Id)' != '%(Identity)' " />
|
|
|
|
<!-- Remove reference items that have been resolved to a LatestPackageReference item. -->
|
|
<PackageReference Include="@(_PrivatePackageReferenceWithVersion)" IsImplicitlyDefined="true" />
|
|
<Reference Remove="@(_PrivatePackageReferenceWithVersion)" />
|
|
|
|
<!-- Free up memory for unnecessary items -->
|
|
<_LatestPackageReferenceWithVersion Remove="@(_LatestPackageReferenceWithVersion)" />
|
|
<_BaselinePackageReferenceWithVersion Remove="@(_BaselinePackageReferenceWithVersion)" />
|
|
<_PrivatePackageReferenceWithVersion Remove="@(_PrivatePackageReferenceWithVersion)" />
|
|
<_ImplicitPackageReference Remove="@(_ImplicitPackageReference)" />
|
|
</ItemGroup>
|
|
|
|
<Error Condition="'$(DisablePackageReferenceRestrictions)' != 'true' AND @(_ExplicitPackageReference->Count()) != 0"
|
|
Text="PackageReference items are not allowed. Use <Reference> instead to replace the reference to @(_ExplicitPackageReference, ', '). See docs/ReferenceResolution.md for more details." />
|
|
|
|
<ItemGroup>
|
|
<_ExplicitPackageReference Remove="@(_ExplicitPackageReference)" />
|
|
</ItemGroup>
|
|
|
|
<Warning Condition="'$(IsReferenceAssemblyProject)' != 'true' AND '$(IsServicingBuild)' != 'true' AND '%(UnusedBaselinePackageReference.Identity)' != ''"
|
|
Code="BUILD001"
|
|
Text="Reference to '%(UnusedBaselinePackageReference.Identity)' was removed since the last stable release of this package. This could be a breaking change. See docs/ReferenceResolution.md for instructions on how to update changes to references or suppress this warning if the error was intentional." />
|
|
|
|
<Error Condition="'$(IsReferenceAssemblyProject)' != 'true' AND '$(IsServicingBuild)' == 'true' AND @(UnusedBaselinePackageReference->Count()) != 0"
|
|
Code="BUILD002"
|
|
Text="Package references changed since the last release. This could be a breaking change and is not allowed in a servicing update. References removed:%0A - @(UnusedBaselinePackageReference, '%0A -')" />
|
|
|
|
<Error Condition="'$(TargetFrameworkIdentifier)' != '.NETFramework' AND '%(Reference.Identity)' != '' AND ! Exists('%(Reference.Identity)') AND '$(DisablePackageReferenceRestrictions)' != 'true'"
|
|
Code="MSB3245"
|
|
Text="Could not resolve this reference. Could not locate the package or project for "%(Reference.Identity)". Did you update baselines and dependencies lists? See docs/ReferenceResolution.md for more details." />
|
|
</Target>
|
|
|
|
<!-- These targets are used to generate the map of assembly name to project files. See also the /t:GenerateProjectList target in build/repo.targets. -->
|
|
<Target Name="GetReferencesProvided" Returns="@(ProvidesReference)">
|
|
<ItemGroup>
|
|
<_TargetFramework Remove="@(_TargetFramework)" />
|
|
<_TargetFramework Include="$(TargetFramework)" Condition="'$(TargetFramework)' != '' "/>
|
|
<_TargetFramework Include="$(TargetFrameworks)" Condition="'$(TargetFramework)' == '' "/>
|
|
</ItemGroup>
|
|
|
|
<MSBuild Projects="$(MSBuildProjectFullPath)"
|
|
Targets="_GetReferencesProvided"
|
|
Properties="TargetFramework=%(_TargetFramework.Identity)">
|
|
<Output TaskParameter="TargetOutputs" ItemName="ProvidesReference" />
|
|
</MSBuild>
|
|
</Target>
|
|
|
|
<Target Name="_GetReferencesProvided" Returns="@(ProvidesReference)">
|
|
<PropertyGroup>
|
|
<ReferenceAssemblyDirectory>$(MSBuildProjectDirectory)/../ref/</ReferenceAssemblyDirectory>
|
|
<ReferenceAssemblyProjectFileRelativePath>$([MSBuild]::MakeRelative($(RepoRoot), '$(ReferenceAssemblyDirectory)$(MSBuildProjectFile)'))</ReferenceAssemblyProjectFileRelativePath>
|
|
</PropertyGroup>
|
|
|
|
<Error Condition="'$(SkipRefDirectoryCheck)' != 'true' AND '$(IsImplementationProject)' == 'true' AND '$(HasReferenceAssembly)' != 'true' AND Exists($(ReferenceAssemblyDirectory))" Text="Project shouldn't have reference assembly but folder exists $(ReferenceAssemblyDirectory)" />
|
|
<Error Condition=" '$(IsAspNetCoreApp)' == 'true' AND '$(IsImplementationProject)' == 'true' AND '$(HasReferenceAssembly)' != 'true'" Text="All assemblies which have set IsAspNetCoreApp=true should produce a reference assembly." />
|
|
|
|
<ItemGroup Condition=" '$(IsProjectReferenceProvider)' == 'true' ">
|
|
<ProvidesReference Include="$(AssemblyName)">
|
|
<IsAspNetCoreApp>$([MSBuild]::ValueOrDefault($(IsAspNetCoreApp),'false'))</IsAspNetCoreApp>
|
|
<IsPackable>$([MSBuild]::ValueOrDefault($(IsPackable),'false'))</IsPackable>
|
|
<ProjectFileRelativePath>$([MSBuild]::MakeRelative($(RepoRoot), $(MSBuildProjectFullPath)))</ProjectFileRelativePath>
|
|
<ReferenceAssemblyProjectFileRelativePath Condition="'$(HasReferenceAssembly)' == 'true'">$(ReferenceAssemblyProjectFileRelativePath)</ReferenceAssemblyProjectFileRelativePath>
|
|
</ProvidesReference>
|
|
</ItemGroup>
|
|
</Target>
|
|
|
|
<!-- This is used by the eng/scripts/AddAllProjectRefsToSolution.ps1 script to traverse the ProjectRef graph -->
|
|
<PropertyGroup>
|
|
<_CustomCollectProjectReferenceDependsOn Condition="'$(TargetFramework)' != ''">ResolveProjectReferences</_CustomCollectProjectReferenceDependsOn>
|
|
</PropertyGroup>
|
|
<Target Name="_CustomCollectProjectReference" DependsOnTargets="$(_CustomCollectProjectReferenceDependsOn)" Returns="$(MSBuildProjectFullPath);@(_MSBuildProjectReferenceExistent)">
|
|
<ItemGroup>
|
|
<_TargetFrameworks Include="$(TargetFrameworks)" />
|
|
</ItemGroup>
|
|
<MSBuild Condition="'$(TargetFramework)' == ''"
|
|
Targets="_CustomCollectProjectReference"
|
|
BuildInParallel="true"
|
|
Projects="$(MSBuildProjectFullPath)"
|
|
Properties="TargetFramework=%(_TargetFrameworks.Identity)"
|
|
RebaseOutputs="True">
|
|
<Output TaskParameter="TargetOutputs" ItemName="_MSBuildProjectReferenceExistent" />
|
|
</MSBuild>
|
|
<MSBuild Condition="'$(TargetFramework)' != ''"
|
|
Targets="_CustomCollectProjectReference"
|
|
BuildInParallel="true"
|
|
SkipNonexistentTargets="true"
|
|
Projects="@(_MSBuildProjectReferenceExistent)"
|
|
RebaseOutputs="True">
|
|
<Output TaskParameter="TargetOutputs" ItemName="_MSBuildProjectReferenceExistent" />
|
|
</MSBuild>
|
|
</Target>
|
|
</Project> |