Skip to content

Commit 82bef91

Browse files
baronfelsurayya-MS
andauthored
ensure that single-rid container publishes populate all container information (#48584)
Co-authored-by: Surayya Huseyn Zada <[email protected]>
1 parent 24f646c commit 82bef91

File tree

2 files changed

+33
-18
lines changed

2 files changed

+33
-18
lines changed

src/Containers/packaging/build/Microsoft.NET.Build.Containers.targets

Lines changed: 28 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,8 @@
4141
<ContainerRuntimeIdentifier Condition="'$(ContainerRuntimeIdentifier)' == '' and '$(RuntimeIdentifier)' != ''">$(RuntimeIdentifier)</ContainerRuntimeIdentifier>
4242
<ContainerRuntimeIdentifiers Condition="'$(BuildingInsideVisualStudio)' != 'true' and '$(ContainerRuntimeIdentifiers)' == '' and '$(IsRidAgnostic)' != 'true'">$(RuntimeIdentifiers)</ContainerRuntimeIdentifiers>
4343
<ContainerRuntimeIdentifier Condition="'$(ContainerRuntimeIdentifier)' == '' and '$(ContainerRuntimeIdentifiers)' == ''">linux-$(NETCoreSdkPortableRuntimeIdentifier.Split('-')[1])</ContainerRuntimeIdentifier>
44+
<!-- We want to save customer provided ContainerBaseImage to later set ContainerUser. -->
45+
<_InitialContainerBaseImage>$(ContainerBaseImage)</_InitialContainerBaseImage>
4446
</PropertyGroup>
4547

4648
<ItemGroup>
@@ -67,7 +69,9 @@
6769
</ItemGroup>
6870
</Target>
6971

70-
<Target Name="ComputeContainerConfig" DependsOnTargets="ComputeContainerBaseImage">
72+
<!-- This Target is called early on in the chain for both single-RID and multi-RID containers - but for single-RID it's important
73+
that we ensure all of the data necessary to create a single-RID container is computed after we exit this target. -->
74+
<Target Name="ComputeContainerConfig" DependsOnTargets="ComputeContainerBaseImage;_ComputeContainerExecutionArgs">
7175
<PropertyGroup Label="VS defaults">
7276
<!-- RegistryUrl is used by existing VS targets for Docker builds - this lets us fill that void -->
7377
<ContainerRegistry Condition="'$(RegistryUrl)' != ''">$(RegistryUrl)</ContainerRegistry>
@@ -177,26 +181,27 @@
177181
<PropertyGroup>
178182
<PublishContainerDependsOn>
179183
_ContainerVerifySDKVersion;
184+
_ContainerEstablishRIDNess;
180185
ComputeContainerConfig;
181186
_CheckContainersPackage
182187
</PublishContainerDependsOn>
183188
</PropertyGroup>
184189

185190
<!-- These args are relevant to container execution and are per-RID by nature. Therefore they're a direct dependency of the _PublishSingleContainer
186-
target and not computed at the outer layer. -->
187-
<Target Name="_ComputeContainerExecutionArgs">
191+
target and not computed at the outer, multi-RID build layer. -->
192+
<Target Name="_ComputeContainerExecutionArgs" Condition="'$(_IsSingleRIDBuild)' == 'true'">
188193
<PropertyGroup>
189194
<!-- The Container RID should default to the RID used for the entire build (to ensure things run on the platform they are built for), but the user knows best and so should be able to set it explicitly.
190195
For builds that have a RID, we default to that RID. Otherwise, we default to the Linux RID matching the architecture of the currently-executing SDK. -->
191196
<_ContainerIsTargetingWindows>false</_ContainerIsTargetingWindows>
192197
<_ContainerIsTargetingWindows Condition="$(ContainerRuntimeIdentifier.StartsWith('win'))">true</_ContainerIsTargetingWindows>
193-
198+
194199
<!-- Set the WorkingDirectory depending on the RID -->
195200
<ContainerWorkingDirectory Condition="'$(ContainerWorkingDirectory)' == '' and !$(_ContainerIsTargetingWindows)">/app/</ContainerWorkingDirectory>
196201
<ContainerWorkingDirectory Condition="'$(ContainerWorkingDirectory)' == '' and $(_ContainerIsTargetingWindows)">C:\app\</ContainerWorkingDirectory>
197-
198-
<_ContainerIsUsingMicrosoftDefaultImages Condition="'$(ContainerBaseImage)' == ''">true</_ContainerIsUsingMicrosoftDefaultImages>
199-
<_ContainerIsUsingMicrosoftDefaultImages Condition="'$(ContainerBaseImage)' != ''">false</_ContainerIsUsingMicrosoftDefaultImages>
202+
203+
<_ContainerIsUsingMicrosoftDefaultImages Condition="'$(_InitialContainerBaseImage)' == ''">true</_ContainerIsUsingMicrosoftDefaultImages>
204+
<_ContainerIsUsingMicrosoftDefaultImages Condition="'$(_InitialContainerBaseImage)' != ''">false</_ContainerIsUsingMicrosoftDefaultImages>
200205
</PropertyGroup>
201206

202207
<!-- We only set a default user when the base image is Microsoft-authored, and we're targeting a version of those images that supports a nonroot user -->
@@ -245,7 +250,9 @@
245250
Text="The $(_ContainersPackageIdentity) NuGet package is explicitly referenced but the current SDK can natively publish the project as a container. Consider removing the package reference to $(_ContainersPackageIdentity) because it is no longer needed." />
246251
</Target>
247252

248-
<Target Name="_PublishSingleContainer" DependsOnTargets="_ComputeContainerExecutionArgs" Returns="@(GeneratedContainer)">
253+
<!-- There is an implicit dependency here in that both of ComputeContainerConfig and _ComputeContainerExecutionArgs must have been run, but because we call this Target
254+
in a few different ways we can't express that dependency directly here. -->
255+
<Target Name="_PublishSingleContainer" Returns="@(GeneratedContainer)">
249256
<PropertyGroup Condition="'$(DOTNET_HOST_PATH)' == ''">
250257
<DotNetHostDirectory>$(NetCoreRoot)</DotNetHostDirectory>
251258
<DotNetHostFileName>dotnet</DotNetHostFileName>
@@ -342,14 +349,17 @@
342349
ContainerGenerateLabels=$(ContainerGenerateLabels);
343350
ContainerGenerateLabelsImageBaseDigest=$(ContainerGenerateLabelsImageBaseDigest);
344351
_SkipContainerPublishing=$(_SkipContainerPublishing);
345-
ContainerImageFormat=$(_SingleImageContainerFormat)
352+
ContainerImageFormat=$(_SingleImageContainerFormat);
353+
_IsMultiRIDBuild=false;
354+
_IsSingleRIDBuild=true;
355+
_InitialContainerBaseImage=$(_InitialContainerBaseImage)
346356
"/>
347357
<_rids Remove ="$(_rids)" />
348358
</ItemGroup>
349359

350360
<MSBuild
351361
Projects="@(_InnerBuild)"
352-
Targets="Publish;_ParseItemsForPublishingSingleContainer;_PublishSingleContainer"
362+
Targets="Publish;_ParseItemsForPublishingSingleContainer;_ComputeContainerExecutionArgs;_PublishSingleContainer"
353363
BuildInParallel="$([MSBuild]::ValueOrDefault('$(ContainerPublishInParallel)', 'true'))">
354364
<Output TaskParameter="TargetOutputs" ItemName="GeneratedContainer" />
355365
</MSBuild>
@@ -401,11 +411,7 @@
401411
</ItemGroup>
402412
</Target>
403413

404-
<Target Name="PublishContainer"
405-
DependsOnTargets="$(PublishContainerDependsOn)"
406-
Condition="'$(IsPublishable)' == 'true' AND '$(EnableSdkContainerSupport)' == 'true'"
407-
Returns="@(GeneratedContainer)"
408-
>
414+
<Target Name="_ContainerEstablishRIDNess">
409415
<PropertyGroup>
410416
<_IsMultiTFMBuild Condition="'$(TargetFrameworks)' != '' and '$(TargetFramework)' == ''">true</_IsMultiTFMBuild>
411417
<!-- we are multi-RID if:
@@ -415,10 +421,17 @@
415421
<_HasCRIDsAndNoCRID Condition="'$(ContainerRuntimeIdentifiers)' != '' and '$(ContainerRuntimeIdentifier)' == ''">true</_HasCRIDsAndNoCRID>
416422
<_HasRIDs Condition="'$(RuntimeIdentifiers)' != ''">true</_HasRIDs>
417423
<_NoCRIDsOrCRIDorRID Condition="'$(ContainerRuntimeIdentifiers)' == '' and '$(ContainerRuntimeIdentifier)' == '' and '$(RuntimeIdentifier)' == ''">true</_NoCRIDsOrCRIDorRID>
424+
<!-- these two are load-bearing for other comparisons - see _ComputeContainerExecutionArgs -->
418425
<_IsMultiRIDBuild Condition="'$(BuildingInsideVisualStudio)' != 'true' and ('$(_HasCRIDsAndNoCRID)' == true or ('$(_HasRIDs)' == 'true' and '$(_NoCRIDsOrCRIDorRID)' == 'true'))">true</_IsMultiRIDBuild>
419426
<_IsSingleRIDBuild Condition="'$(_IsMultiRIDBuild)' == ''">true</_IsSingleRIDBuild>
420427
</PropertyGroup>
428+
</Target>
421429

430+
<Target Name="PublishContainer"
431+
DependsOnTargets="$(PublishContainerDependsOn)"
432+
Condition="'$(IsPublishable)' == 'true' AND '$(EnableSdkContainerSupport)' == 'true'"
433+
Returns="@(GeneratedContainer)"
434+
>
422435
<!-- Call _PublishMultiArchContainers if we are in a multi-rid build, and call _PublishSingleContainer if we are in a single-RID build -->
423436
<CallTarget Condition="'$(_IsMultiRIDBuild)' == 'true' " Targets="_PublishMultiArchContainers">
424437
<Output TaskParameter="TargetOutputs" ItemName="GeneratedContainer" />

test/Microsoft.NET.Build.Containers.IntegrationTests/TargetsTests.cs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,12 @@ public void CanDeferContainerAppCommand(
2222
{
2323
[prop] = value.ToString(),
2424
[ContainerRuntimeIdentifier] = $"{os}-x64",
25+
["_IsSingleRIDBuild"] = "true",
2526

2627
}, projectName: $"{nameof(CanDeferContainerAppCommand)}_{prop}_{value}_{string.Join("_", expectedAppCommandArgs)}");
2728
using var _ = d;
2829
var instance = project.CreateProjectInstance(ProjectInstanceSettings.None);
29-
instance.Build([ _ComputeContainerExecutionArgs ], []);
30+
instance.Build([ ComputeContainerConfig ], []);
3031
var computedAppCommand = instance.GetItems(ContainerAppCommand).Select(i => i.EvaluatedInclude);
3132

3233
// The test was not testing anything previously, as the list returned was zero length,
@@ -310,11 +311,12 @@ public void CanComputeContainerUser(string tfm, string rid, string? expectedUser
310311
["TargetFrameworkIdentifier"] = ".NETCoreApp",
311312
["TargetFrameworkVersion"] = tfm,
312313
["TargetFramework"] = "net" + tfm.TrimStart('v'),
313-
["ContainerRuntimeIdentifier"] = rid
314+
["ContainerRuntimeIdentifier"] = rid,
315+
["_IsSingleRIDBuild"] = "true",
314316
}, projectName: $"{nameof(CanComputeContainerUser)}_{tfm}_{rid}_{expectedUser}");
315317
using var _ = d;
316318
var instance = project.CreateProjectInstance(ProjectInstanceSettings.None);
317-
instance.Build(new[] { _ComputeContainerExecutionArgs }, new[] { logger }, null, out var outputs).Should().BeTrue(String.Join(Environment.NewLine, logger.Errors));
319+
instance.Build(new[] { ComputeContainerConfig }, new[] { logger }, null, out var outputs).Should().BeTrue(String.Join(Environment.NewLine, logger.Errors));
318320
var computedTag = instance.GetProperty("ContainerUser")?.EvaluatedValue;
319321
computedTag.Should().Be(expectedUser);
320322
}

0 commit comments

Comments
 (0)