From d573aabcf639c21d999aabcc7c0513eed8cd28ee Mon Sep 17 00:00:00 2001 From: Nick Josevski Date: Tue, 8 Sep 2026 21:01:50 +1000 Subject: [PATCH] Run gzip directly in BuildDockerImages instead of through pwsh BuildDockerImages launched PowerShell for exactly one thing: running `gzip -k -9 -f` on the OCI tar. That made the step depend on whichever .NET runtime the agent's `pwsh` global tool was built against, and on main's build agent those no longer line up: App: /root/.dotnet/tools/pwsh Framework: 'Microsoft.NETCore.App', version '10.0.0' .NET location: .../.nuke/temp/dotnet-unix The following frameworks were found: 8.0.30 The agent's `pwsh` needs .NET 10, and the only runtime on offer is the .NET 8 SDK that build.sh bootstraps into .nuke/temp and puts on PATH. Calling gzip directly removes pwsh from the equation. This was the build's only use of PowerShellTasks, so nothing else in the build cares about the agent's pwsh now. Failures also surface properly. `pwsh -Command` exits 0 regardless of the native exit code, so a failed gzip used to show up later as a confusing missing-artifact error from PublishArtifacts. A Nuke Tool asserts a zero exit code, so it now fails at the gzip call with gzip's stderr attached. Verified with a throwaway target: resolves /usr/bin/gzip from PATH, arguments pass through intact, -k keeps the .tar alongside the .gz, and a deliberate failure raises `ProcessException: Process 'gzip' exited with code 1`. Not addressed here: reaching the SDK bootstrap at all means `dotnet --version` failed, so the agent no longer satisfies global.json's 8.0.419 pin. That costs every build a full SDK download and belongs with the .NET 10 work. Co-Authored-By: Claude Opus 5 (1M context) --- build/Build.Docker.cs | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/build/Build.Docker.cs b/build/Build.Docker.cs index c9bf2006f..585b83b93 100644 --- a/build/Build.Docker.cs +++ b/build/Build.Docker.cs @@ -1,12 +1,15 @@ using Calamari.Build.Utilities; using JetBrains.Annotations; +using Nuke.Common.Tooling; using Nuke.Common.Tools.Docker; -using Nuke.Common.Tools.PowerShell; namespace Calamari.Build; public partial class Build { + //Resolved from PATH so a missing gzip fails by name, rather than as a mystery exit code + static Tool Gzip => ToolResolver.GetPathTool("gzip"); + [PublicAPI] Target BuildDockerImages => d => @@ -82,10 +85,10 @@ public partial class Build return settings; }); - //compress with gzip - PowerShellTasks.PowerShell(_ => _ - .EnableNoProfile() - .SetCommand($"gzip -k -9 -f '{outputFile}'")); + //compress with gzip. Invoked directly rather than via pwsh, which only + //added a dependency on whatever .NET runtime the agent's `pwsh` global tool + //was built against - not the SDK this build pins. + Gzip($"-k -9 -f \"{outputFile}\""); //gzip always uses the .gz suffix var compressedZipPath = $"{outputFile}.gz";