From 29cb1ce2f4b2c5af8b7445734dac152d1c1812c9 Mon Sep 17 00:00:00 2001 From: Hayato Kiwata Date: Sun, 21 Dec 2025 01:00:58 +0900 Subject: [PATCH 1/2] fix: use private namespace for image build in private namespace In the current implementation, tests that require nerdtest.Build do not run against the specified namespace when a private namespace is configured. For example, with the following requirements, the test runs in a private namespace, but the internal logic of nerdtest.Build does not take the private namespace into account, causing buildctl or buildkit to be unavailable: ``` testCase.Require = require.All( nerdtest.Private, nerdtest.Build, ) ``` This commit fixes the behavior so that when a private namespace is specified, tests are executed considering that namespace instead of the default namespace. Signed-off-by: Hayato Kiwata --- pkg/testutil/nerdtest/requirements.go | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/pkg/testutil/nerdtest/requirements.go b/pkg/testutil/nerdtest/requirements.go index d4af8490339..11c8e399113 100644 --- a/pkg/testutil/nerdtest/requirements.go +++ b/pkg/testutil/nerdtest/requirements.go @@ -337,7 +337,12 @@ var Build = &test.Requirement{ mess := "buildkitd is enabled" if isTargetNerdish() { - bkHostAddr, err := buildkitutil.GetBuildkitHost(defaultNamespace) + namespace := defaultNamespace + if ns := helpers.Read(Namespace); ns != "" { + namespace = string(ns) + } + + bkHostAddr, err := buildkitutil.GetBuildkitHost(namespace) if err != nil { ret = false mess = fmt.Sprintf("buildkitd is not enabled: %+v", err) From 4a95d73245ff19835b09a3696281281833439061 Mon Sep 17 00:00:00 2001 From: Hayato Kiwata Date: Sun, 21 Dec 2025 01:06:42 +0900 Subject: [PATCH 2/2] test: refactor compose_create_linux_test.go to use Tigron Signed-off-by: Hayato Kiwata --- .../compose/compose_create_linux_test.go | 191 +++++++++++++----- 1 file changed, 143 insertions(+), 48 deletions(-) diff --git a/cmd/nerdctl/compose/compose_create_linux_test.go b/cmd/nerdctl/compose/compose_create_linux_test.go index a62d9b14104..581681e00e8 100644 --- a/cmd/nerdctl/compose/compose_create_linux_test.go +++ b/cmd/nerdctl/compose/compose_create_linux_test.go @@ -18,12 +18,15 @@ package compose import ( "fmt" + "path/filepath" + "regexp" "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/mod/tigron/tig" @@ -147,82 +150,174 @@ services: } func TestComposeCreatePull(t *testing.T) { + testCase := nerdtest.Setup() - base := testutil.NewBase(t) - var dockerComposeYAML = fmt.Sprintf(` + testCase.NoParallel = true + testCase.Require = nerdtest.Private + + testCase.Setup = func(data test.Data, helpers test.Helpers) { + composeYAML := fmt.Sprintf(` services: svc0: image: %s `, testutil.CommonImage) - comp := testutil.NewComposeDir(t, dockerComposeYAML) - defer comp.CleanUp() - projectName := comp.ProjectName() - t.Logf("projectName=%q", projectName) - - defer base.ComposeCmd("-f", comp.YAMLFullPath(), "down", "-v").AssertOK() - - // `compose create --pull never` should fail: no such image - base.Cmd("rmi", "-f", testutil.CommonImage).Run() - base.ComposeCmd("-f", comp.YAMLFullPath(), "create", "--pull", "never").AssertFail() - // `compose create --pull missing(default)|always` should succeed: image is pulled and container is created - base.Cmd("rmi", "-f", testutil.CommonImage).Run() - base.ComposeCmd("-f", comp.YAMLFullPath(), "create").AssertOK() - base.Cmd("rmi", "-f", testutil.CommonImage).Run() - base.ComposeCmd("-f", comp.YAMLFullPath(), "create", "--pull", "always").AssertOK() - base.ComposeCmd("-f", comp.YAMLFullPath(), "ps", "svc0", "-a").AssertOutContainsAny("Created", "created") + composePath := data.Temp().Save(composeYAML, "compose.yaml") + + projectName := filepath.Base(filepath.Dir(composePath)) + t.Logf("projectName=%q", projectName) + + data.Labels().Set("composeYAML", composePath) + } + + testCase.SubTests = []*test.Case{ + { + Description: "compose create --pull never fails when image missing", + NoParallel: true, + Setup: func(data test.Data, helpers test.Helpers) { + helpers.Ensure("rmi", "-f", testutil.CommonImage) + }, + Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { + return helpers.Command("compose", "-f", data.Labels().Get("composeYAML"), "create", "--pull", "never") + }, + Expected: test.Expects(1, nil, nil), + }, + { + Description: "compose create --pull missing (default) pulls and creates a container", + NoParallel: true, + Setup: func(data test.Data, helpers test.Helpers) { + helpers.Ensure("rmi", "-f", testutil.CommonImage) + helpers.Ensure("compose", "-f", data.Labels().Get("composeYAML"), "create") + }, + Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { + return helpers.Command("compose", "-f", data.Labels().Get("composeYAML"), "ps", "svc0", "-a") + }, + Expected: test.Expects(0, nil, expect.Match(regexp.MustCompile(`Created|created`))), + }, + { + Description: "compose create --pull always pulls and creates a container", + NoParallel: true, + Setup: func(data test.Data, helpers test.Helpers) { + helpers.Ensure("rmi", "-f", testutil.CommonImage) + helpers.Ensure("compose", "-f", data.Labels().Get("composeYAML"), "create", "--pull", "always") + }, + Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { + return helpers.Command("compose", "-f", data.Labels().Get("composeYAML"), "ps", "svc0", "-a") + }, + Expected: test.Expects(0, nil, expect.Match(regexp.MustCompile(`Created|created`))), + }, + } + + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if data.Labels().Get("composeYAML") != "" { + helpers.Anyhow("compose", "-f", data.Labels().Get("composeYAML"), "down", "-v") + } + } + + testCase.Run(t) } func TestComposeCreateBuild(t *testing.T) { - const imageSvc0 = "composebuild_svc0" + testCase := nerdtest.Setup() - dockerComposeYAML := fmt.Sprintf(` + testCase.NoParallel = true + testCase.Require = require.All( + nerdtest.Private, + nerdtest.Build, + ) + + testCase.Setup = func(data test.Data, helpers test.Helpers) { + imageSvc0 := data.Identifier("composebuild_svc0") + composeYAML := fmt.Sprintf(` services: svc0: build: . image: %s `, imageSvc0) + dockerfile := fmt.Sprintf(`FROM %s`, testutil.CommonImage) - dockerfile := fmt.Sprintf(`FROM %s`, testutil.CommonImage) + composePath := data.Temp().Save(composeYAML, "compose.yaml") + data.Temp().Save(dockerfile, "Dockerfile") - testutil.RequiresBuild(t) - testutil.RegisterBuildCacheCleanup(t) - base := testutil.NewBase(t) + projectName := filepath.Base(filepath.Dir(composePath)) + t.Logf("projectName=%q", projectName) - comp := testutil.NewComposeDir(t, dockerComposeYAML) - defer comp.CleanUp() - comp.WriteFile("Dockerfile", dockerfile) - projectName := comp.ProjectName() - t.Logf("projectName=%q", projectName) + data.Labels().Set("composeYAML", composePath) + data.Labels().Set("imageName", imageSvc0) + } - defer base.Cmd("rmi", imageSvc0).Run() - defer base.ComposeCmd("-f", comp.YAMLFullPath(), "down", "-v").AssertOK() + testCase.SubTests = []*test.Case{ + { + Description: "compose create --no-build fails when image needs to be built", + NoParallel: true, + Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { + return helpers.Command("compose", "-f", data.Labels().Get("composeYAML"), "create", "--no-build") + }, + Expected: test.Expects(1, nil, nil), + }, + { + Description: "compose create --build builds image and creates container", + NoParallel: true, + Setup: func(data test.Data, helpers test.Helpers) { + helpers.Ensure("compose", "-f", data.Labels().Get("composeYAML"), "create", "--build") + helpers.Command("compose", "-f", data.Labels().Get("composeYAML"), "images", "svc0").Run( + &test.Expected{ + ExitCode: 0, + Output: func(stdout string, t tig.T) { + assert.Assert(t, strings.Contains(stdout, data.Labels().Get("imageName"))) + }, + }, + ) + }, + Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { + return helpers.Command("compose", "-f", data.Labels().Get("composeYAML"), "ps", "svc0", "-a") + }, + Expected: test.Expects(0, nil, expect.Match(regexp.MustCompile(`Created|created`))), + }, + } - // `compose create --no-build` should fail if service image needs build - base.ComposeCmd("-f", comp.YAMLFullPath(), "create", "--no-build").AssertFail() - // `compose create --build` should succeed: image is built and container is created - base.ComposeCmd("-f", comp.YAMLFullPath(), "create", "--build").AssertOK() - base.ComposeCmd("-f", comp.YAMLFullPath(), "images", "svc0").AssertOutContains(imageSvc0) - base.ComposeCmd("-f", comp.YAMLFullPath(), "ps", "svc0", "-a").AssertOutContainsAny("Created", "created") + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if data.Labels().Get("composeYAML") != "" { + helpers.Anyhow("compose", "-f", data.Labels().Get("composeYAML"), "down", "-v") + } + helpers.Anyhow("rmi", "-f", data.Labels().Get("imageName")) + helpers.Anyhow("builder", "prune", "--all", "--force") + } + + testCase.Run(t) } func TestComposeCreateWritesConfigHashLabel(t *testing.T) { - var dockerComposeYAML = fmt.Sprintf(` + testCase := nerdtest.Setup() + + testCase.Setup = func(data test.Data, helpers test.Helpers) { + var composeYAML = fmt.Sprintf(` services: svc0: image: %s `, testutil.CommonImage) + composePath := data.Temp().Save(composeYAML, "compose.yaml") + + projectName := filepath.Base(filepath.Dir(composePath)) + t.Logf("projectName=%q", projectName) - base := testutil.NewBase(t) - comp := testutil.NewComposeDir(t, dockerComposeYAML) - defer comp.CleanUp() - projectName := comp.ProjectName() - t.Logf("projectName=%q", projectName) + data.Labels().Set("composeYAML", composePath) + data.Labels().Set("containerName", serviceparser.DefaultContainerName(projectName, "svc0", "1")) - base.ComposeCmd("-f", comp.YAMLFullPath(), "create").AssertOK() - defer base.ComposeCmd("-f", comp.YAMLFullPath(), "down", "-v").Run() + helpers.Ensure("compose", "-f", composePath, "create") + } + + testCase.Command = func(data test.Data, helpers test.Helpers) test.TestableCommand { + return helpers.Command("inspect", "--format", "{{json .Config.Labels}}", data.Labels().Get("containerName")) + } + + testCase.Expected = test.Expects(0, nil, expect.Contains("com.docker.compose.config-hash")) - container := serviceparser.DefaultContainerName(projectName, "svc0", "1") - base.Cmd("inspect", "--format", "{{json .Config.Labels}}", container). - AssertOutContains("com.docker.compose.config-hash") + testCase.Cleanup = func(data test.Data, helpers test.Helpers) { + if path := data.Labels().Get("composeYAML"); path != "" { + helpers.Anyhow("compose", "-f", path, "down", "-v") + } + } + + testCase.Run(t) }