From 3fed4adabc6d8df8ac3a6a2bff59b0867176c152 Mon Sep 17 00:00:00 2001 From: Ogulcan Aydogan Date: Thu, 14 May 2026 08:20:36 +0100 Subject: [PATCH 1/5] refactor: migrate multi_platform_linux_test.go to nerdtest.Setup Replace testutil.NewBase with nerdtest.Setup throughout multi_platform_linux_test.go, following the Tigron framework pattern (#4641). Changes: - Use nerdtest.RegistryWithNoAuth instead of testregistry.NewWithNoAuth - Use data.Temp().Save() for Dockerfiles and compose files - Convert testMultiPlatformRun helper to use test.Helpers - Use SubTests in TestMultiPlatformRun for per-platform isolation - Register builder cache cleanup in Cleanup callbacks - Add requireMultiPlatformExec requirement using platformutil Signed-off-by: Ogulcan Aydogan --- .../container/multi_platform_linux_test.go | 302 ++++++++++++------ 1 file changed, 206 insertions(+), 96 deletions(-) diff --git a/cmd/nerdctl/container/multi_platform_linux_test.go b/cmd/nerdctl/container/multi_platform_linux_test.go index 01ae208528c..c9d37a2ab75 100644 --- a/cmd/nerdctl/container/multi_platform_linux_test.go +++ b/cmd/nerdctl/container/multi_platform_linux_test.go @@ -22,17 +22,35 @@ import ( "strings" "testing" - "gotest.tools/v3/assert" + "github.com/containerd/nerdctl/mod/tigron/expect" + "github.com/containerd/nerdctl/mod/tigron/require" + "github.com/containerd/nerdctl/mod/tigron/test" - "github.com/containerd/nerdctl/v2/cmd/nerdctl/helpers" + "github.com/containerd/nerdctl/v2/pkg/platformutil" "github.com/containerd/nerdctl/v2/pkg/testutil" + "github.com/containerd/nerdctl/v2/pkg/testutil/nerdtest" "github.com/containerd/nerdctl/v2/pkg/testutil/nettestutil" - "github.com/containerd/nerdctl/v2/pkg/testutil/testregistry" ) -func testMultiPlatformRun(base *testutil.Base, alpineImage string) { - t := base.T - testutil.RequireExecPlatform(t, "linux/amd64", "linux/arm64", "linux/arm/v7") +// requireMultiPlatformExec skips the test when the host cannot execute +// linux/amd64, linux/arm64 and linux/arm/v7 images (e.g. no binfmt_misc). +var requireMultiPlatformExec = &test.Requirement{ + Check: func(_ test.Data, _ test.Helpers) (bool, string) { + ok, err := platformutil.CanExecProbably("linux/amd64", "linux/arm64", "linux/arm/v7") + if !ok { + msg := "requires multi-platform exec support (linux/amd64, linux/arm64, linux/arm/v7)" + if err != nil { + msg += ": " + err.Error() + } + return false, msg + } + return true, "" + }, +} + +// assertMultiPlatformRun runs uname -m inside image on each platform and +// asserts the expected machine type string. +func assertMultiPlatformRun(helpers test.Helpers, image string) { testCases := map[string]string{ "amd64": "x86_64", "arm64": "aarch64", @@ -41,92 +59,165 @@ func testMultiPlatformRun(base *testutil.Base, alpineImage string) { "linux/arm/v7": "armv7l", } for plat, expectedUnameM := range testCases { - t.Logf("Testing %q (%q)", plat, expectedUnameM) - cmd := base.Cmd("run", "--rm", "--platform="+plat, alpineImage, "uname", "-m") - cmd.AssertOutExactly(expectedUnameM + "\n") + helpers.T().Log(fmt.Sprintf("Testing platform %q (%q)", plat, expectedUnameM)) + helpers.Command("run", "--rm", "--platform="+plat, image, "uname", "-m"). + Run(&test.Expected{ + Output: expect.Equals(expectedUnameM + "\n"), + }) } } func TestMultiPlatformRun(t *testing.T) { - base := testutil.NewBase(t) - testMultiPlatformRun(base, testutil.AlpineImage) + testCase := nerdtest.Setup() + + testCase.Require = requireMultiPlatformExec + + testCasePlatforms := map[string]string{ + "amd64": "x86_64", + "arm64": "aarch64", + "arm": "armv7l", + "linux/arm": "armv7l", + "linux/arm/v7": "armv7l", + } + for plat, expectedUnameM := range testCasePlatforms { + p, e := plat, expectedUnameM + testCase.SubTests = append(testCase.SubTests, &test.Case{ + Description: p, + Command: test.Command("run", "--rm", "--platform="+p, testutil.AlpineImage, "uname", "-m"), + Expected: test.Expects(0, nil, expect.Equals(e+"\n")), + }) + } + + testCase.Run(t) } func TestMultiPlatformBuildPush(t *testing.T) { - testutil.DockerIncompatible(t) // non-buildx version of `docker build` lacks multi-platform. Also, `docker push` lacks --platform. - testutil.RequiresBuild(t) - testutil.RegisterBuildCacheCleanup(t) - testutil.RequireExecPlatform(t, "linux/amd64", "linux/arm64", "linux/arm/v7") - base := testutil.NewBase(t) - tID := testutil.Identifier(t) - reg := testregistry.NewWithNoAuth(base, 0, false) - defer reg.Cleanup(nil) - - imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, tID) - defer base.Cmd("rmi", imageName).Run() - - dockerfile := fmt.Sprintf(`FROM %s -RUN echo dummy - `, testutil.AlpineImage) - - buildCtx := helpers.CreateBuildContext(t, dockerfile) - - base.Cmd("build", "-t", imageName, "--platform=amd64,arm64,linux/arm/v7", buildCtx).AssertOK() - testMultiPlatformRun(base, imageName) - base.Cmd("push", "--platform=amd64,arm64,linux/arm/v7", imageName).AssertOK() + testCase := nerdtest.Setup() + + testCase.Require = require.All( + require.Not(nerdtest.Docker), + nerdtest.Build, + requireMultiPlatformExec, + nerdtest.Registry, + ) + + testCase.Setup = func(data test.Data, helpers test.Helpers) { + reg := nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) + data.Labels().Set("image", imageName) + + dockerfile := fmt.Sprintf("FROM %s\nRUN echo dummy\n", testutil.AlpineImage) + buildCtx := data.Temp().Dir() + data.Temp().Save(dockerfile, "Dockerfile") + + helpers.Ensure("build", "-t", imageName, "--platform=amd64,arm64,linux/arm/v7", buildCtx) + } + + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if img := data.Labels().Get("image"); img != "" { + helpers.Anyhow("rmi", img) + } + helpers.Anyhow("builder", "prune", "--all", "--force") + } + + testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { + imageName := data.Labels().Get("image") + assertMultiPlatformRun(helpers, imageName) + return helpers.Command("push", "--platform=amd64,arm64,linux/arm/v7", imageName) + } + + testCase.Expected = test.Expects(0, nil, nil) + + testCase.Run(t) } -// TestMultiPlatformBuildPushNoRun tests if the push succeeds in a situation where nerdctl builds -// a Dockerfile without RUN, COPY, etc commands. In such situation, BuildKit doesn't download the base image -// so nerdctl needs to ensure these blobs to be locally available. func TestMultiPlatformBuildPushNoRun(t *testing.T) { - testutil.DockerIncompatible(t) // non-buildx version of `docker build` lacks multi-platform. Also, `docker push` lacks --platform. - testutil.RequiresBuild(t) - testutil.RegisterBuildCacheCleanup(t) - testutil.RequireExecPlatform(t, "linux/amd64", "linux/arm64", "linux/arm/v7") - base := testutil.NewBase(t) - tID := testutil.Identifier(t) - reg := testregistry.NewWithNoAuth(base, 0, false) - defer reg.Cleanup(nil) - - imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, tID) - defer base.Cmd("rmi", imageName).Run() - - dockerfile := fmt.Sprintf(`FROM %s -CMD echo dummy - `, testutil.AlpineImage) - - buildCtx := helpers.CreateBuildContext(t, dockerfile) - - base.Cmd("build", "-t", imageName, "--platform=amd64,arm64,linux/arm/v7", buildCtx).AssertOK() - testMultiPlatformRun(base, imageName) - base.Cmd("push", "--platform=amd64,arm64,linux/arm/v7", imageName).AssertOK() + testCase := nerdtest.Setup() + + testCase.Require = require.All( + require.Not(nerdtest.Docker), + nerdtest.Build, + requireMultiPlatformExec, + nerdtest.Registry, + ) + + testCase.Setup = func(data test.Data, helpers test.Helpers) { + reg := nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) + data.Labels().Set("image", imageName) + + dockerfile := fmt.Sprintf("FROM %s\nCMD echo dummy\n", testutil.AlpineImage) + buildCtx := data.Temp().Dir() + data.Temp().Save(dockerfile, "Dockerfile") + + helpers.Ensure("build", "-t", imageName, "--platform=amd64,arm64,linux/arm/v7", buildCtx) + } + + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if img := data.Labels().Get("image"); img != "" { + helpers.Anyhow("rmi", img) + } + helpers.Anyhow("builder", "prune", "--all", "--force") + } + + testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { + imageName := data.Labels().Get("image") + assertMultiPlatformRun(helpers, imageName) + return helpers.Command("push", "--platform=amd64,arm64,linux/arm/v7", imageName) + } + + testCase.Expected = test.Expects(0, nil, nil) + + testCase.Run(t) } func TestMultiPlatformPullPushAllPlatforms(t *testing.T) { - testutil.DockerIncompatible(t) - base := testutil.NewBase(t) - tID := testutil.Identifier(t) - reg := testregistry.NewWithNoAuth(base, 0, false) - defer reg.Cleanup(nil) - - pushImageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, tID) - defer base.Cmd("rmi", pushImageName).Run() - - base.Cmd("pull", "--quiet", "--all-platforms", testutil.AlpineImage).AssertOK() - base.Cmd("tag", testutil.AlpineImage, pushImageName).AssertOK() - base.Cmd("push", "--all-platforms", pushImageName).AssertOK() - testMultiPlatformRun(base, pushImageName) + testCase := nerdtest.Setup() + + testCase.Require = require.All( + require.Not(nerdtest.Docker), + requireMultiPlatformExec, + nerdtest.Registry, + ) + + testCase.Setup = func(data test.Data, helpers test.Helpers) { + reg := nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + pushImageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) + data.Labels().Set("image", pushImageName) + helpers.Ensure("pull", "--quiet", "--all-platforms", testutil.AlpineImage) + helpers.Ensure("tag", testutil.AlpineImage, pushImageName) + } + + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if img := data.Labels().Get("image"); img != "" { + helpers.Anyhow("rmi", img) + } + } + + testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { + pushImageName := data.Labels().Get("image") + helpers.Ensure("push", "--all-platforms", pushImageName) + assertMultiPlatformRun(helpers, pushImageName) + return helpers.Command("inspect", "--type=image", pushImageName) + } + + testCase.Expected = test.Expects(0, nil, nil) + + testCase.Run(t) } func TestMultiPlatformComposeUpBuild(t *testing.T) { - testutil.DockerIncompatible(t) - testutil.RequiresBuild(t) - testutil.RegisterBuildCacheCleanup(t) - testutil.RequireExecPlatform(t, "linux/amd64", "linux/arm64", "linux/arm/v7") - base := testutil.NewBase(t) + testCase := nerdtest.Setup() + + testCase.Require = require.All( + require.Not(nerdtest.Docker), + nerdtest.Build, + requireMultiPlatformExec, + ) - const dockerComposeYAML = ` + testCase.Setup = func(data test.Data, helpers test.Helpers) { + dockerfile := fmt.Sprintf("FROM %s\nRUN uname -m > /usr/share/nginx/html/index.html\n", testutil.NginxAlpineImage) + composeYAML := ` services: svc0: build: . @@ -144,30 +235,49 @@ services: ports: - 8082:80 ` - dockerfile := fmt.Sprintf(`FROM %s -RUN uname -m > /usr/share/nginx/html/index.html -`, testutil.NginxAlpineImage) + buildCtx := data.Temp().Dir() + composePath := data.Temp().Save(composeYAML, "compose.yaml") + _ = buildCtx + data.Temp().Save(dockerfile, "Dockerfile") + data.Labels().Set("composePath", composePath) - comp := testutil.NewComposeDir(t, dockerComposeYAML) - defer comp.CleanUp() - - comp.WriteFile("Dockerfile", dockerfile) - - base.ComposeCmd("-f", comp.YAMLFullPath(), "up", "-d", "--build").AssertOK() - defer base.ComposeCmd("-f", comp.YAMLFullPath(), "down", "-v").Run() + helpers.Ensure("compose", "-f", composePath, "up", "-d", "--build") + } - testCases := map[string]string{ - "http://127.0.0.1:8080": "x86_64", - "http://127.0.0.1:8081": "aarch64", - "http://127.0.0.1:8082": "armv7l", + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if cp := data.Labels().Get("composePath"); cp != "" { + helpers.Anyhow("compose", "-f", cp, "down", "-v") + } + helpers.Anyhow("builder", "prune", "--all", "--force") } - for testURL, expectedIndexHTML := range testCases { - resp, err := nettestutil.HTTPGet(testURL, 5, false) - assert.NilError(t, err) - respBody, err := io.ReadAll(resp.Body) - assert.NilError(t, err) - t.Logf("respBody=%q", respBody) - assert.Assert(t, strings.Contains(string(respBody), expectedIndexHTML)) + testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { + urlExpected := map[string]string{ + "http://127.0.0.1:8080": "x86_64", + "http://127.0.0.1:8081": "aarch64", + "http://127.0.0.1:8082": "armv7l", + } + for url, expected := range urlExpected { + resp, err := nettestutil.HTTPGet(url, 5, false) + if err != nil { + helpers.T().Log(fmt.Sprintf("GET %s: %v", url, err)) + helpers.T().FailNow() + } + body, err := io.ReadAll(resp.Body) + resp.Body.Close() + if err != nil { + helpers.T().Log(fmt.Sprintf("reading body from %s: %v", url, err)) + helpers.T().FailNow() + } + if !strings.Contains(string(body), expected) { + helpers.T().Log(fmt.Sprintf("expected %q in body from %s, got %q", expected, url, string(body))) + helpers.T().Fail() + } + } + return helpers.Command("compose", "-f", data.Labels().Get("composePath"), "ps") } + + testCase.Expected = test.Expects(0, nil, nil) + + testCase.Run(t) } From aeba7c38748634155016fe6474e87b5393e77837 Mon Sep 17 00:00:00 2001 From: Ogulcan Aydogan Date: Thu, 14 May 2026 15:50:10 +0100 Subject: [PATCH 2/5] fix: start and cleanup registry in multi-platform push tests nerdtest.RegistryWithNoAuth returns a Server struct with Setup/Cleanup closures but does not start the registry container automatically. Add reg.Setup(data, helpers) in each test's Setup callback to start the registry before pushing, and reg.Cleanup(data, helpers) in the Cleanup callback to remove the container after the test. Affected: TestMultiPlatformBuildPush, TestMultiPlatformBuildPushNoRun, TestMultiPlatformPullPushAllPlatforms. Signed-off-by: Ogulcan Aydogan --- .../container/multi_platform_linux_test.go | 25 ++++++++++++++++--- 1 file changed, 22 insertions(+), 3 deletions(-) diff --git a/cmd/nerdctl/container/multi_platform_linux_test.go b/cmd/nerdctl/container/multi_platform_linux_test.go index c9d37a2ab75..c5676acc073 100644 --- a/cmd/nerdctl/container/multi_platform_linux_test.go +++ b/cmd/nerdctl/container/multi_platform_linux_test.go @@ -29,6 +29,7 @@ import ( "github.com/containerd/nerdctl/v2/pkg/platformutil" "github.com/containerd/nerdctl/v2/pkg/testutil" "github.com/containerd/nerdctl/v2/pkg/testutil/nerdtest" + "github.com/containerd/nerdctl/v2/pkg/testutil/nerdtest/registry" "github.com/containerd/nerdctl/v2/pkg/testutil/nettestutil" ) @@ -101,8 +102,11 @@ func TestMultiPlatformBuildPush(t *testing.T) { nerdtest.Registry, ) + var reg *registry.Server + testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg := nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg.Setup(data, helpers) imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", imageName) @@ -118,6 +122,9 @@ func TestMultiPlatformBuildPush(t *testing.T) { helpers.Anyhow("rmi", img) } helpers.Anyhow("builder", "prune", "--all", "--force") + if reg != nil { + reg.Cleanup(data, helpers) + } } testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { @@ -141,8 +148,11 @@ func TestMultiPlatformBuildPushNoRun(t *testing.T) { nerdtest.Registry, ) + var reg *registry.Server + testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg := nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg.Setup(data, helpers) imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", imageName) @@ -158,6 +168,9 @@ func TestMultiPlatformBuildPushNoRun(t *testing.T) { helpers.Anyhow("rmi", img) } helpers.Anyhow("builder", "prune", "--all", "--force") + if reg != nil { + reg.Cleanup(data, helpers) + } } testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { @@ -180,8 +193,11 @@ func TestMultiPlatformPullPushAllPlatforms(t *testing.T) { nerdtest.Registry, ) + var reg *registry.Server + testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg := nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg.Setup(data, helpers) pushImageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", pushImageName) helpers.Ensure("pull", "--quiet", "--all-platforms", testutil.AlpineImage) @@ -192,6 +208,9 @@ func TestMultiPlatformPullPushAllPlatforms(t *testing.T) { if img := data.Labels().Get("image"); img != "" { helpers.Anyhow("rmi", img) } + if reg != nil { + reg.Cleanup(data, helpers) + } } testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { From 98ad89521acdcdf356d42f6becf6f713e403aeb7 Mon Sep 17 00:00:00 2001 From: Ogulcan Aydogan Date: Fri, 15 May 2026 12:09:24 +0100 Subject: [PATCH 3/5] refactor: use tigron expect constants for exit codes in multi-platform tests Replace hardcoded 0 literals passed to test.Expects() with expect.ExitCodeSuccess for consistency with the rest of the test suite. Signed-off-by: Ogulcan Aydogan --- cmd/nerdctl/container/multi_platform_linux_test.go | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/cmd/nerdctl/container/multi_platform_linux_test.go b/cmd/nerdctl/container/multi_platform_linux_test.go index c5676acc073..8191b8d7c1c 100644 --- a/cmd/nerdctl/container/multi_platform_linux_test.go +++ b/cmd/nerdctl/container/multi_platform_linux_test.go @@ -85,7 +85,7 @@ func TestMultiPlatformRun(t *testing.T) { testCase.SubTests = append(testCase.SubTests, &test.Case{ Description: p, Command: test.Command("run", "--rm", "--platform="+p, testutil.AlpineImage, "uname", "-m"), - Expected: test.Expects(0, nil, expect.Equals(e+"\n")), + Expected: test.Expects(expect.ExitCodeSuccess, nil, expect.Equals(e+"\n")), }) } @@ -133,7 +133,7 @@ func TestMultiPlatformBuildPush(t *testing.T) { return helpers.Command("push", "--platform=amd64,arm64,linux/arm/v7", imageName) } - testCase.Expected = test.Expects(0, nil, nil) + testCase.Expected = test.Expects(expect.ExitCodeSuccess, nil, nil) testCase.Run(t) } @@ -179,7 +179,7 @@ func TestMultiPlatformBuildPushNoRun(t *testing.T) { return helpers.Command("push", "--platform=amd64,arm64,linux/arm/v7", imageName) } - testCase.Expected = test.Expects(0, nil, nil) + testCase.Expected = test.Expects(expect.ExitCodeSuccess, nil, nil) testCase.Run(t) } @@ -220,7 +220,7 @@ func TestMultiPlatformPullPushAllPlatforms(t *testing.T) { return helpers.Command("inspect", "--type=image", pushImageName) } - testCase.Expected = test.Expects(0, nil, nil) + testCase.Expected = test.Expects(expect.ExitCodeSuccess, nil, nil) testCase.Run(t) } @@ -296,7 +296,7 @@ services: return helpers.Command("compose", "-f", data.Labels().Get("composePath"), "ps") } - testCase.Expected = test.Expects(0, nil, nil) + testCase.Expected = test.Expects(expect.ExitCodeSuccess, nil, nil) testCase.Run(t) } From cf2726d8ca800efbd55000a3be059cbb8065583e Mon Sep 17 00:00:00 2001 From: Ogulcan Aydogan Date: Fri, 15 May 2026 14:31:23 +0100 Subject: [PATCH 4/5] refactor: clarify zero-port argument in RegistryWithNoAuth calls The third argument 0 means "let the OS pick any available port". Add an inline comment to make this clear at the call sites. Signed-off-by: Ogulcan Aydogan --- cmd/nerdctl/container/multi_platform_linux_test.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/cmd/nerdctl/container/multi_platform_linux_test.go b/cmd/nerdctl/container/multi_platform_linux_test.go index 8191b8d7c1c..302fecf3344 100644 --- a/cmd/nerdctl/container/multi_platform_linux_test.go +++ b/cmd/nerdctl/container/multi_platform_linux_test.go @@ -105,7 +105,7 @@ func TestMultiPlatformBuildPush(t *testing.T) { var reg *registry.Server testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg = nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, 0 /* random port */, false) reg.Setup(data, helpers) imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", imageName) @@ -151,7 +151,7 @@ func TestMultiPlatformBuildPushNoRun(t *testing.T) { var reg *registry.Server testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg = nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, 0 /* random port */, false) reg.Setup(data, helpers) imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", imageName) @@ -196,7 +196,7 @@ func TestMultiPlatformPullPushAllPlatforms(t *testing.T) { var reg *registry.Server testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg = nerdtest.RegistryWithNoAuth(data, helpers, 0, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, 0 /* random port */, false) reg.Setup(data, helpers) pushImageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", pushImageName) From a1ad17d882ade78e2aed0beba676309d0406ef6e Mon Sep 17 00:00:00 2001 From: Ogulcan Aydogan Date: Sat, 16 May 2026 23:10:32 +0100 Subject: [PATCH 5/5] refactor: use named constants for port and exit code in tests Signed-off-by: Ogulcan Aydogan --- cmd/nerdctl/container/multi_platform_linux_test.go | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/cmd/nerdctl/container/multi_platform_linux_test.go b/cmd/nerdctl/container/multi_platform_linux_test.go index 302fecf3344..63a1f14aa72 100644 --- a/cmd/nerdctl/container/multi_platform_linux_test.go +++ b/cmd/nerdctl/container/multi_platform_linux_test.go @@ -33,6 +33,9 @@ import ( "github.com/containerd/nerdctl/v2/pkg/testutil/nettestutil" ) +// randomPort asks the registry helpers to acquire a free port automatically. +const randomPort = 0 + // requireMultiPlatformExec skips the test when the host cannot execute // linux/amd64, linux/arm64 and linux/arm/v7 images (e.g. no binfmt_misc). var requireMultiPlatformExec = &test.Requirement{ @@ -63,7 +66,8 @@ func assertMultiPlatformRun(helpers test.Helpers, image string) { helpers.T().Log(fmt.Sprintf("Testing platform %q (%q)", plat, expectedUnameM)) helpers.Command("run", "--rm", "--platform="+plat, image, "uname", "-m"). Run(&test.Expected{ - Output: expect.Equals(expectedUnameM + "\n"), + ExitCode: expect.ExitCodeSuccess, + Output: expect.Equals(expectedUnameM + "\n"), }) } } @@ -105,7 +109,7 @@ func TestMultiPlatformBuildPush(t *testing.T) { var reg *registry.Server testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg = nerdtest.RegistryWithNoAuth(data, helpers, 0 /* random port */, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, randomPort, false) reg.Setup(data, helpers) imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", imageName) @@ -151,7 +155,7 @@ func TestMultiPlatformBuildPushNoRun(t *testing.T) { var reg *registry.Server testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg = nerdtest.RegistryWithNoAuth(data, helpers, 0 /* random port */, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, randomPort, false) reg.Setup(data, helpers) imageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", imageName) @@ -196,7 +200,7 @@ func TestMultiPlatformPullPushAllPlatforms(t *testing.T) { var reg *registry.Server testCase.Setup = func(data test.Data, helpers test.Helpers) { - reg = nerdtest.RegistryWithNoAuth(data, helpers, 0 /* random port */, false) + reg = nerdtest.RegistryWithNoAuth(data, helpers, randomPort, false) reg.Setup(data, helpers) pushImageName := fmt.Sprintf("localhost:%d/%s:latest", reg.Port, data.Identifier()) data.Labels().Set("image", pushImageName)