-
Notifications
You must be signed in to change notification settings - Fork 4.7k
/
resolveContract.targets
155 lines (132 loc) · 9.86 KB
/
resolveContract.targets
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
<Project>
<!--
##### Contract project settings #####
- Allows referencing contract projects for passing matching reference assemblies to tooling like ApiCompat.
- Allows building against contract assemblies when referencing source projects.
-->
<PropertyGroup>
<ContractProject Condition="'$(ContractProject)' == ''">$(LibrariesProjectRoot)$(MSBuildProjectName)\ref\$(MSBuildProjectName).csproj</ContractProject>
<HasMatchingContract Condition="'$(HasMatchingContract)' == '' and Exists('$(ContractProject)')">true</HasMatchingContract>
<!-- Don't build against reference assemblies when projects are packable and the tfm is not the latest .NETCoreApp as
such reference assemblies don't ship to customers and only exist for tooling scenarios. -->
<AnnotateTargetPathWithContract Condition="'$(AnnotateTargetPathWithContract)' == '' and
'$(HasMatchingContract)' == 'true' and
(
'$(IsPackable)' != 'true' or
(
'$(TargetFrameworkIdentifier)' == '.NETCoreApp' and
'$(TargetFrameworkVersion)' == 'v$(NetCoreAppCurrentVersion)'
)
)">true</AnnotateTargetPathWithContract>
</PropertyGroup>
<ItemGroup Condition="'$(HasMatchingContract)' == 'true' and '$(ContractProject)' != ''">
<ProjectReference Include="$(ContractProject)" ReferenceOutputAssembly="false" OutputItemType="ResolvedMatchingContract" />
</ItemGroup>
<!-- We aren't referencing the contract, but make sure it's considered as an input to Compile so that if it changes we rebuild and rerun API compat -->
<Target Name="AddResolvedMatchingContractToCompileInput"
BeforeTargets="CoreCompile"
AfterTargets="ResolveProjectReferences"
Condition="'@(ResolvedMatchingContract)' != ''">
<ItemGroup>
<CustomAdditionalCompileInputs Include="@(ResolvedMatchingContract)" />
</ItemGroup>
</Target>
<!-- Allow P2Ps that target a source project to build against the corresponding ref project. -->
<Target Name="AnnotateTargetPathWithTargetPlatformMonikerWithReferenceAssembly"
Condition="'$(AnnotateTargetPathWithContract)' == 'true'"
DependsOnTargets="ResolveProjectReferences"
AfterTargets="GetTargetPathWithTargetPlatformMoniker">
<ItemGroup>
<TargetPathWithTargetPlatformMoniker ReferenceAssembly="@(ResolvedMatchingContract)" />
</ItemGroup>
</Target>
<!-- ##### APICompat settings ##### -->
<PropertyGroup>
<ApiCompatContractItemName>ResolvedMatchingContract</ApiCompatContractItemName>
<ApiCompatStrictMode Condition="'$(ApiCompatStrictMode)' == ''">true</ApiCompatStrictMode>
<!-- Optional rules -->
<ApiCompatEnableRuleAttributesMustMatch>true</ApiCompatEnableRuleAttributesMustMatch>
<ApiCompatEnableRuleCannotChangeParameterName>true</ApiCompatEnableRuleCannotChangeParameterName>
<_ApiCompatCaptureGroupPattern>.+%5C$([System.IO.Path]::DirectorySeparatorChar)(.+)%5C$([System.IO.Path]::DirectorySeparatorChar)(.+)</_ApiCompatCaptureGroupPattern>
<_ApiCompatRuntimePrefixPattern>(.+)/(net%5Cd.%5Cd)-(.+)/(.+)</_ApiCompatRuntimePrefixPattern>
<_ApiCompatLibReplacementString>lib/$1/$2</_ApiCompatLibReplacementString>
<!-- CoreLib source projects have different output paths. -->
<_ApiCompatLibReplacementString Condition="'$(MSBuildProjectName)' == 'System.Private.CoreLib'">lib/$(NetCoreAppCurrent)/$2</_ApiCompatLibReplacementString>
</PropertyGroup>
<PropertyGroup Condition="'$(IsCrossTargetingBuild)' != 'true'">
<!-- Disable API compat if the project doesn't have a reference assembly. -->
<ApiCompatValidateAssemblies Condition="'$(HasMatchingContract)' != 'true'">false</ApiCompatValidateAssemblies>
<!-- TODO: Move into Microsoft.DotNet.GenFacadesNotSupported.targets. -->
<!-- Not supported sources are created from the ref assembly, we currently don't produce finalizers in dummy assemblies, so we disable ApiCompat to not fail. -->
<ApiCompatValidateAssemblies Condition="'$(GeneratePlatformNotSupportedAssemblyMessage)' != ''">false</ApiCompatValidateAssemblies>
</PropertyGroup>
<ItemGroup>
<ApiCompatExcludeAttributesFile Include="$(RepositoryEngineeringDir)DefaultGenApiDocIds.txt" />
<ApiCompatExcludeAttributesFile Include="$(RepositoryEngineeringDir)ApiCompatExcludeAttributes.txt" />
</ItemGroup>
<ItemGroup>
<!-- Transform the API Compat assemblies passed in to log-able strings. -->
<ApiCompatLeftAssembliesTransformationPattern Include="$(_ApiCompatCaptureGroupPattern)" ReplacementString="ref/$1/$2" />
<ApiCompatLeftAssembliesTransformationPattern Include="$(_ApiCompatRuntimePrefixPattern)" ReplacementString="runtimes/$3/$1/$2/$4" />
<ApiCompatLeftAssembliesTransformationPattern Include="runtimes/windows/" ReplacementString="runtimes/win/" />
<ApiCompatRightAssembliesTransformationPattern Include="$(_ApiCompatCaptureGroupPattern)" ReplacementString="$(_ApiCompatLibReplacementString)" />
<ApiCompatRightAssembliesTransformationPattern Include="$(_ApiCompatRuntimePrefixPattern)" ReplacementString="runtimes/$3/$1/$2/$4" />
<ApiCompatRightAssembliesTransformationPattern Include="runtimes/windows/" ReplacementString="runtimes/win/" />
<!-- Fall back to the targeting pack dir for NetCoreAppCurrent to avoid passing through dependencies from ref to src. -->
<ApiCompatContractAssemblyReferences Include="$(MicrosoftNetCoreAppRefPackRefDir)"
Condition="$([MSBuild]::IsTargetFrameworkCompatible('$(TargetFramework)', '$(NetCoreAppCurrent)'))" />
</ItemGroup>
<!-- Use the apicompat task package instead of the in-built SDK functionality to consume newer features. -->
<ItemGroup Condition="'$(EnablePackageValidation)' == 'true' or
'$(ApiCompatValidateAssemblies)' == 'true'">
<PackageReference Include="Microsoft.DotNet.ApiCompat.Task" Version="$(MicrosoftDotNetApiCompatTaskVersion)" PrivateAssets="all" IsImplicitlyDefined="true" />
</ItemGroup>
<!-- ##### GenAPI settings ##### -->
<PropertyGroup>
<GenAPIExcludeAttributesList>$(RepositoryEngineeringDir)DefaultGenApiDocIds.txt</GenAPIExcludeAttributesList>
<GenAPIHeaderFile>$(RepositoryEngineeringDir)LicenseHeader.txt</GenAPIHeaderFile>
<GenAPITargetPath>$([MSBuild]::NormalizePath('$(MSBuildProjectDirectory)', '..', 'ref', '$(AssemblyName).cs'))</GenAPITargetPath>
<GenAPILangVersion Condition="'$(LangVersion)' != ''">$(LangVersion)</GenAPILangVersion>
<ProjectForGenAPIDocIdGeneration Condition="'$(ProjectForGenAPIDocIdGeneration)' == ''">$(CoreLibProject)</ProjectForGenAPIDocIdGeneration>
</PropertyGroup>
<ItemGroup>
<!-- GenAPI is currently only invoked on demand and not used as part of the build as it isn't source build compatible. -->
<PackageReference Include="Microsoft.DotNet.GenAPI"
Version="$(MicrosoftDotNetGenApiVersion)"
PrivateAssets="all"
IsImplicitlyDefined="true"
Condition="'$(DotNetBuildFromSource)' != 'true'" />
</ItemGroup>
<!-- Generate a .txt file with all public types of the project referenced by ProjectForGenAPIDocIdGeneration (e.g. System.Private.CoreLib or System.Private.Uri implementation assembly).
This file is then later on passed to GenAPI as the list of types which should be "split out" with the conditional compilation logic. -->
<Target Name="GenerateConditionalTypeLists"
Condition="'@(ProjectReference)' != '' and @(ProjectReference->AnyHaveMetadataValue('Identity', '$(ProjectForGenAPIDocIdGeneration)')) and ('$(ContractTypesPartiallyMoved)' == 'true' or '$(ContractTypesPartiallyMoved)' == 'true')">
<PropertyGroup>
<!-- We either wrap all contract types in a #if condition (when SymbolForGenAPIConditionalTypeLists is empty),
or just the types mentioned in GenAPIConditionalTypeLists with the symbol specified in SymbolForGenAPIConditionalTypeLists -->
<GenAPIDefaultCondition Condition="'$(SymbolForGenAPIConditionalTypeLists)' == ''">!BUILDING_CORELIB_REFERENCE</GenAPIDefaultCondition>
</PropertyGroup>
<ItemGroup>
<_genAPILibPathForGenAPIDocIdGeneration Include="@(ReferencePath->'%(RootDir)%(Directory)'->Distinct())" />
<_genAPIResolvedProjectForGenAPIDocIdGeneration Include="@(_ResolvedProjectReferencePaths->WithMetadataValue('MSBuildSourceProjectFile','$(ProjectForGenAPIDocIdGeneration)'))" />
<GenAPIConditionalTypeLists Include="$(IntermediateOutputPath)GenAPIConditionalTypeList.txt">
<Symbol Condition="'$(SymbolForGenAPIConditionalTypeLists)' != ''">$(SymbolForGenAPIConditionalTypeLists)</Symbol>
</GenAPIConditionalTypeLists>
</ItemGroup>
<!-- Generate conditional compilation symbols to hide types implemented in contracts so we can include the .cs in the System.Private.CoreLib ref -->
<Microsoft.DotNet.GenAPI.GenAPITask
Assembly="@(_genAPIResolvedProjectForGenAPIDocIdGeneration)"
LibPath="@(_genAPILibPathForGenAPIDocIdGeneration)"
WriterType="DocIds"
DocIdKinds="Namespace, Type"
OutputPath="@(GenAPIConditionalTypeLists)" />
</Target>
<Target Name="SetGenAPIProperties"
DependsOnTargets="GenerateConditionalTypeLists"
BeforeTargets="GenerateReferenceAssemblySource">
<PropertyGroup>
<GenAPIFollowTypeForwards Condition="'%(ProjectReference.Identity)' == '$(CoreLibProject)' or '%(ProjectReference.Identity)' == '$(UriProject)'">true</GenAPIFollowTypeForwards>
</PropertyGroup>
</Target>
<Import Project="$(RepositoryEngineeringDir)outerBuild.targets" Condition="'$(IsCrossTargetingBuild)' == 'true'" />
</Project>