From 060734b868fe71a55bdfa2a9293add71caf794ff Mon Sep 17 00:00:00 2001 From: Kevin Wittek Date: Tue, 17 Sep 2024 14:26:06 +0200 Subject: [PATCH 1/5] fix(postgres): Apply default snapshot name if no name specified (#2783) --- modules/postgres/options.go | 2 + modules/postgres/postgres.go | 1 + modules/postgres/postgres_test.go | 138 +++++++++++++++++------------- 3 files changed, 83 insertions(+), 58 deletions(-) diff --git a/modules/postgres/options.go b/modules/postgres/options.go index ad24c79fc3..5779f85c04 100644 --- a/modules/postgres/options.go +++ b/modules/postgres/options.go @@ -7,11 +7,13 @@ import ( type options struct { // SQLDriverName is the name of the SQL driver to use. SQLDriverName string + Snapshot string } func defaultOptions() options { return options{ SQLDriverName: "postgres", + Snapshot: defaultSnapshotName, } } diff --git a/modules/postgres/postgres.go b/modules/postgres/postgres.go index a6bc418ff3..b4b59663a2 100644 --- a/modules/postgres/postgres.go +++ b/modules/postgres/postgres.go @@ -177,6 +177,7 @@ func Run(ctx context.Context, img string, opts ...testcontainers.ContainerCustom password: req.Env["POSTGRES_PASSWORD"], user: req.Env["POSTGRES_USER"], sqlDriverName: settings.SQLDriverName, + snapshotName: settings.Snapshot, } } diff --git a/modules/postgres/postgres_test.go b/modules/postgres/postgres_test.go index 825a5bdc6f..505fb3b05c 100644 --- a/modules/postgres/postgres_test.go +++ b/modules/postgres/postgres_test.go @@ -203,73 +203,95 @@ func TestWithInitScript(t *testing.T) { } func TestSnapshot(t *testing.T) { - // snapshotAndReset { - ctx := context.Background() - - // 1. Start the postgres ctr and run any migrations on it - ctr, err := postgres.Run( - ctx, - "docker.io/postgres:16-alpine", - postgres.WithDatabase(dbname), - postgres.WithUsername(user), - postgres.WithPassword(password), - postgres.BasicWaitStrategies(), - postgres.WithSQLDriver("pgx"), - ) - testcontainers.CleanupContainer(t, ctr) - require.NoError(t, err) - - // Run any migrations on the database - _, _, err = ctr.Exec(ctx, []string{"psql", "-U", user, "-d", dbname, "-c", "CREATE TABLE users (id SERIAL, name TEXT NOT NULL, age INT NOT NULL)"}) - require.NoError(t, err) + tests := []struct { + name string + options []postgres.SnapshotOption + }{ + { + name: "snapshot/default", + options: nil, + }, - // 2. Create a snapshot of the database to restore later - err = ctr.Snapshot(ctx, postgres.WithSnapshotName("test-snapshot")) - require.NoError(t, err) + { + name: "snapshot/custom", + options: []postgres.SnapshotOption{ + postgres.WithSnapshotName("custom-snapshot"), + }, + }, + } - dbURL, err := ctr.ConnectionString(ctx) - require.NoError(t, err) + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + // snapshotAndReset { + ctx := context.Background() - t.Run("Test inserting a user", func(t *testing.T) { - t.Cleanup(func() { - // 3. In each test, reset the DB to its snapshot state. - err = ctr.Restore(ctx) + // 1. Start the postgres ctr and run any migrations on it + ctr, err := postgres.Run( + ctx, + "docker.io/postgres:16-alpine", + postgres.WithDatabase(dbname), + postgres.WithUsername(user), + postgres.WithPassword(password), + postgres.BasicWaitStrategies(), + postgres.WithSQLDriver("pgx"), + ) + testcontainers.CleanupContainer(t, ctr) require.NoError(t, err) - }) - conn, err := pgx.Connect(context.Background(), dbURL) - require.NoError(t, err) - defer conn.Close(context.Background()) - - _, err = conn.Exec(ctx, "INSERT INTO users(name, age) VALUES ($1, $2)", "test", 42) - require.NoError(t, err) - - var name string - var age int64 - err = conn.QueryRow(context.Background(), "SELECT name, age FROM users LIMIT 1").Scan(&name, &age) - require.NoError(t, err) - - require.Equal(t, "test", name) - require.EqualValues(t, 42, age) - }) + // Run any migrations on the database + _, _, err = ctr.Exec(ctx, []string{"psql", "-U", user, "-d", dbname, "-c", "CREATE TABLE users (id SERIAL, name TEXT NOT NULL, age INT NOT NULL)"}) + require.NoError(t, err) - // 4. Run as many tests as you need, they will each get a clean database - t.Run("Test querying empty DB", func(t *testing.T) { - t.Cleanup(func() { - err = ctr.Restore(ctx) + // 2. Create a snapshot of the database to restore later + // tt.options comes the test case, it can be specified as e.g. `postgres.WithSnapshotName("custom-snapshot")` or omitted, to use default name + err = ctr.Snapshot(ctx, tt.options...) require.NoError(t, err) - }) - conn, err := pgx.Connect(context.Background(), dbURL) - require.NoError(t, err) - defer conn.Close(context.Background()) + dbURL, err := ctr.ConnectionString(ctx) + require.NoError(t, err) - var name string - var age int64 - err = conn.QueryRow(context.Background(), "SELECT name, age FROM users LIMIT 1").Scan(&name, &age) - require.ErrorIs(t, err, pgx.ErrNoRows) - }) - // } + t.Run("Test inserting a user", func(t *testing.T) { + t.Cleanup(func() { + // 3. In each test, reset the DB to its snapshot state. + err = ctr.Restore(ctx) + require.NoError(t, err) + }) + + conn, err := pgx.Connect(context.Background(), dbURL) + require.NoError(t, err) + defer conn.Close(context.Background()) + + _, err = conn.Exec(ctx, "INSERT INTO users(name, age) VALUES ($1, $2)", "test", 42) + require.NoError(t, err) + + var name string + var age int64 + err = conn.QueryRow(context.Background(), "SELECT name, age FROM users LIMIT 1").Scan(&name, &age) + require.NoError(t, err) + + require.Equal(t, "test", name) + require.EqualValues(t, 42, age) + }) + + // 4. Run as many tests as you need, they will each get a clean database + t.Run("Test querying empty DB", func(t *testing.T) { + t.Cleanup(func() { + err = ctr.Restore(ctx) + require.NoError(t, err) + }) + + conn, err := pgx.Connect(context.Background(), dbURL) + require.NoError(t, err) + defer conn.Close(context.Background()) + + var name string + var age int64 + err = conn.QueryRow(context.Background(), "SELECT name, age FROM users LIMIT 1").Scan(&name, &age) + require.ErrorIs(t, err, pgx.ErrNoRows) + }) + // } + }) + } } func TestSnapshotWithOverrides(t *testing.T) { From e2bd70faa82e7338c56d352f79a13314215d9371 Mon Sep 17 00:00:00 2001 From: Simon Gate Date: Wed, 18 Sep 2024 01:26:57 +0200 Subject: [PATCH 2/5] feat(mongodb): Wait for mongodb module with a replicaset to finish (#2777) * Insert a document in mongodb during tests To be able to catch `NotWritablePrimary` error * Add mongo:7 to replica set tests * Add new waiting strategy for mongodb replicaset * Extend default wait strategy Thanks @stevenh --------- Co-authored-by: Steven Hartland --- modules/mongodb/mongodb.go | 5 +++++ modules/mongodb/mongodb_test.go | 13 ++++++++++++- 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/modules/mongodb/mongodb.go b/modules/mongodb/mongodb.go index 4923473593..3f73e5dc70 100644 --- a/modules/mongodb/mongodb.go +++ b/modules/mongodb/mongodb.go @@ -3,6 +3,7 @@ package mongodb import ( "context" "fmt" + "time" "github.com/testcontainers/testcontainers-go" "github.com/testcontainers/testcontainers-go/wait" @@ -89,6 +90,10 @@ func WithPassword(password string) testcontainers.CustomizeRequestOption { func WithReplicaSet(replSetName string) testcontainers.CustomizeRequestOption { return func(req *testcontainers.GenericContainerRequest) error { req.Cmd = append(req.Cmd, "--replSet", replSetName) + req.WaitingFor = wait.ForAll( + req.WaitingFor, + wait.ForExec(eval("rs.status().ok")), + ).WithDeadline(60 * time.Second) req.LifecycleHooks = append(req.LifecycleHooks, testcontainers.ContainerLifecycleHooks{ PostStarts: []testcontainers.ContainerHook{ func(ctx context.Context, c testcontainers.Container) error { diff --git a/modules/mongodb/mongodb_test.go b/modules/mongodb/mongodb_test.go index 663f05cff6..03d669bb7e 100644 --- a/modules/mongodb/mongodb_test.go +++ b/modules/mongodb/mongodb_test.go @@ -5,6 +5,7 @@ import ( "testing" "github.com/stretchr/testify/require" + "go.mongodb.org/mongo-driver/bson" "go.mongodb.org/mongo-driver/mongo" "go.mongodb.org/mongo-driver/mongo/options" @@ -48,6 +49,13 @@ func TestMongoDB(t *testing.T) { mongodb.WithReplicaSet("rs"), }, }, + { + name: "With Replica set and mongo:7", + img: "mongo:7", + opts: []testcontainers.ContainerCustomizer{ + mongodb.WithReplicaSet("rs"), + }, + }, } for _, tc := range testCases { @@ -67,12 +75,15 @@ func TestMongoDB(t *testing.T) { // Force direct connection to the container to avoid the replica set // connection string that is returned by the container itself when // using the replica set option. - mongoClient, err := mongo.Connect(ctx, options.Client().ApplyURI(endpoint+"/?connect=direct")) + mongoClient, err := mongo.Connect(ctx, options.Client().ApplyURI(endpoint).SetDirect(true)) require.NoError(tt, err) err = mongoClient.Ping(ctx, nil) require.NoError(tt, err) require.Equal(t, "test", mongoClient.Database("test").Name()) + + _, err = mongoClient.Database("testcontainer").Collection("test").InsertOne(context.Background(), bson.M{}) + require.NoError(tt, err) }) } } From 31a033c5ff201ea3b75a85d702cd98a2de39eca6 Mon Sep 17 00:00:00 2001 From: Rafal Zajac Date: Wed, 18 Sep 2024 14:32:48 +0200 Subject: [PATCH 3/5] fix: do not override ImageBuildOptions.Labels when building from a Dockerfile (#2775) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Fix #2632 - ImageBuildOptions.Labels are overwritten * Fix #2632 - fix linter errors. * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Update container.go Co-authored-by: Manuel de la Peña * Update internal/core/labels.go Co-authored-by: Manuel de la Peña * Update container_test.go Co-authored-by: Manuel de la Peña * Fix #2632 - remove given, when, then comments. * Update internal/core/labels.go Co-authored-by: Manuel de la Peña * Fix #2632 - unit test update. * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Fix #2632 - return error when destination labels map is nil and custom labels are present. * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Update internal/core/labels.go Co-authored-by: Steven Hartland * Update internal/core/labels.go Co-authored-by: Steven Hartland * Update internal/core/labels.go Co-authored-by: Steven Hartland * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Update internal/core/labels_test.go Co-authored-by: Steven Hartland * Fix #2632 - fix test. * Update container_test.go Co-authored-by: Manuel de la Peña --------- Co-authored-by: Steven Hartland Co-authored-by: Manuel de la Peña --- container.go | 9 +++++- container_test.go | 59 ++++++++++++++++++++++++++++++++++++ internal/core/labels.go | 20 ++++++++++++ internal/core/labels_test.go | 34 +++++++++++++++++++++ 4 files changed, 121 insertions(+), 1 deletion(-) create mode 100644 internal/core/labels_test.go diff --git a/container.go b/container.go index 8747335a28..54d89c08e5 100644 --- a/container.go +++ b/container.go @@ -460,7 +460,14 @@ func (c *ContainerRequest) BuildOptions() (types.ImageBuildOptions, error) { } if !c.ShouldKeepBuiltImage() { - buildOptions.Labels = core.DefaultLabels(core.SessionID()) + dst := GenericLabels() + if err = core.MergeCustomLabels(dst, c.Labels); err != nil { + return types.ImageBuildOptions{}, err + } + if err = core.MergeCustomLabels(dst, buildOptions.Labels); err != nil { + return types.ImageBuildOptions{}, err + } + buildOptions.Labels = dst } // Do this as late as possible to ensure we don't leak the context on error/panic. diff --git a/container_test.go b/container_test.go index 074a818569..0cca97e6f5 100644 --- a/container_test.go +++ b/container_test.go @@ -11,6 +11,7 @@ import ( "testing" "time" + "github.com/docker/docker/api/types" "github.com/docker/docker/api/types/container" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" @@ -302,6 +303,64 @@ func Test_BuildImageWithContexts(t *testing.T) { } } +func TestCustomLabelsImage(t *testing.T) { + const ( + myLabelName = "org.my.label" + myLabelValue = "my-label-value" + ) + + ctx := context.Background() + req := testcontainers.GenericContainerRequest{ + ContainerRequest: testcontainers.ContainerRequest{ + Image: "alpine:latest", + Labels: map[string]string{myLabelName: myLabelValue}, + }, + } + + ctr, err := testcontainers.GenericContainer(ctx, req) + + require.NoError(t, err) + t.Cleanup(func() { assert.NoError(t, ctr.Terminate(ctx)) }) + + ctrJSON, err := ctr.Inspect(ctx) + require.NoError(t, err) + assert.Equal(t, myLabelValue, ctrJSON.Config.Labels[myLabelName]) +} + +func TestCustomLabelsBuildOptionsModifier(t *testing.T) { + const ( + myLabelName = "org.my.label" + myLabelValue = "my-label-value" + myBuildOptionLabel = "org.my.bo.label" + myBuildOptionValue = "my-bo-label-value" + ) + + ctx := context.Background() + req := testcontainers.GenericContainerRequest{ + ContainerRequest: testcontainers.ContainerRequest{ + FromDockerfile: testcontainers.FromDockerfile{ + Context: "./testdata", + Dockerfile: "Dockerfile", + BuildOptionsModifier: func(opts *types.ImageBuildOptions) { + opts.Labels = map[string]string{ + myBuildOptionLabel: myBuildOptionValue, + } + }, + }, + Labels: map[string]string{myLabelName: myLabelValue}, + }, + } + + ctr, err := testcontainers.GenericContainer(ctx, req) + testcontainers.CleanupContainer(t, ctr) + require.NoError(t, err) + + ctrJSON, err := ctr.Inspect(ctx) + require.NoError(t, err) + require.Equal(t, myLabelValue, ctrJSON.Config.Labels[myLabelName]) + require.Equal(t, myBuildOptionValue, ctrJSON.Config.Labels[myBuildOptionLabel]) +} + func Test_GetLogsFromFailedContainer(t *testing.T) { ctx := context.Background() // directDockerHubReference { diff --git a/internal/core/labels.go b/internal/core/labels.go index 58b054ab95..b5da2fb29d 100644 --- a/internal/core/labels.go +++ b/internal/core/labels.go @@ -1,6 +1,10 @@ package core import ( + "errors" + "fmt" + "strings" + "github.com/testcontainers/testcontainers-go/internal" ) @@ -21,3 +25,19 @@ func DefaultLabels(sessionID string) map[string]string { LabelVersion: internal.Version, } } + +// MergeCustomLabels sets labels from src to dst. +// If a key in src has [LabelBase] prefix returns an error. +// If dst is nil returns an error. +func MergeCustomLabels(dst, src map[string]string) error { + if dst == nil { + return errors.New("destination map is nil") + } + for key, value := range src { + if strings.HasPrefix(key, LabelBase) { + return fmt.Errorf("key %q has %q prefix", key, LabelBase) + } + dst[key] = value + } + return nil +} diff --git a/internal/core/labels_test.go b/internal/core/labels_test.go new file mode 100644 index 0000000000..e382a0ad48 --- /dev/null +++ b/internal/core/labels_test.go @@ -0,0 +1,34 @@ +package core + +import ( + "testing" + + "github.com/stretchr/testify/require" +) + +func TestMergeCustomLabels(t *testing.T) { + t.Run("success", func(t *testing.T) { + dst := map[string]string{"A": "1", "B": "2"} + src := map[string]string{"B": "X", "C": "3"} + + err := MergeCustomLabels(dst, src) + require.NoError(t, err) + require.Equal(t, map[string]string{"A": "1", "B": "X", "C": "3"}, dst) + }) + + t.Run("invalid-prefix", func(t *testing.T) { + dst := map[string]string{"A": "1", "B": "2"} + src := map[string]string{"B": "X", LabelLang: "go"} + + err := MergeCustomLabels(dst, src) + + require.EqualError(t, err, `key "org.testcontainers.lang" has "org.testcontainers" prefix`) + require.Equal(t, map[string]string{"A": "1", "B": "X"}, dst) + }) + + t.Run("nil-destination", func(t *testing.T) { + src := map[string]string{"A": "1"} + err := MergeCustomLabels(nil, src) + require.Error(t, err) + }) +} From 069f7248cc14b9f8edfcb31c56e1481d1332170e Mon Sep 17 00:00:00 2001 From: Vivek Chandela <107602480+vchandela@users.noreply.github.com> Date: Thu, 19 Sep 2024 01:42:54 +0530 Subject: [PATCH 4/5] fix: handle 127 error code for podman compatibility (#2778) * fix: handle 127 error code for podman compatibility * fix: remove magic numbers; handle 126 and 127 error code separately * chore: handle comments for removing exitStatus type; handle returned error and switch case instead of if-else-if * feat: add unit test for exit code 127 * chore: add internalCheck() tests for exit code = 126/127 * chore: replace t.fatal() with require.NoError() * chore: merge internal check tests with existing tests; revert mockStrategyTarget to MockStrategyTarget to avoid export errors; run make lint --- wait/host_port.go | 33 ++++++++++++----- wait/host_port_test.go | 81 ++++++++++++++++++++++++++++++++++++++---- 2 files changed, 99 insertions(+), 15 deletions(-) diff --git a/wait/host_port.go b/wait/host_port.go index a3e9137006..9360517a04 100644 --- a/wait/host_port.go +++ b/wait/host_port.go @@ -13,13 +13,21 @@ import ( "github.com/docker/go-connections/nat" ) +const ( + exitEaccess = 126 // container cmd can't be invoked (permission denied) + exitCmdNotFound = 127 // container cmd not found/does not exist or invalid bind-mount +) + // Implement interface var ( _ Strategy = (*HostPortStrategy)(nil) _ StrategyTimeout = (*HostPortStrategy)(nil) ) -var errShellNotExecutable = errors.New("/bin/sh command not executable") +var ( + errShellNotExecutable = errors.New("/bin/sh command not executable") + errShellNotFound = errors.New("/bin/sh command not found") +) type HostPortStrategy struct { // Port is a string containing port number and protocol in the format "80/tcp" @@ -151,12 +159,16 @@ func (hp *HostPortStrategy) WaitUntilReady(ctx context.Context, target StrategyT } if err = internalCheck(ctx, internalPort, target); err != nil { - if errors.Is(errShellNotExecutable, err) { + switch { + case errors.Is(err, errShellNotExecutable): log.Println("Shell not executable in container, only external port validated") return nil + case errors.Is(err, errShellNotFound): + log.Println("Shell not found in container") + return nil + default: + return fmt.Errorf("internal check: %w", err) } - - return fmt.Errorf("internal check: %w", err) } return nil @@ -207,13 +219,18 @@ func internalCheck(ctx context.Context, internalPort nat.Port, target StrategyTa return fmt.Errorf("%w, host port waiting failed", err) } - if exitCode == 0 { - break - } else if exitCode == 126 { + // Docker has a issue which override exit code 127 to 126 due to: + // https://github.com/moby/moby/issues/45795 + // Handle both to ensure compatibility with Docker and Podman for now. + switch exitCode { + case 0: + return nil + case exitEaccess: return errShellNotExecutable + case exitCmdNotFound: + return errShellNotFound } } - return nil } func buildInternalCheckCommand(internalPort int) string { diff --git a/wait/host_port_test.go b/wait/host_port_test.go index bf349f05a7..18a15aed82 100644 --- a/wait/host_port_test.go +++ b/wait/host_port_test.go @@ -1,8 +1,10 @@ package wait import ( + "bytes" "context" "io" + "log" "net" "strconv" "testing" @@ -456,16 +458,12 @@ func TestHostPortStrategyFailsWhileInternalCheckingDueToUnexpectedContainerStatu func TestHostPortStrategySucceedsGivenShellIsNotInstalled(t *testing.T) { listener, err := net.Listen("tcp", "localhost:0") - if err != nil { - t.Fatal(err) - } + require.NoError(t, err) defer listener.Close() rawPort := listener.Addr().(*net.TCPAddr).Port port, err := nat.NewPort("tcp", strconv.Itoa(rawPort)) - if err != nil { - t.Fatal(err) - } + require.NoError(t, err) target := &MockStrategyTarget{ HostImpl: func(_ context.Context) (string, error) { @@ -497,7 +495,67 @@ func TestHostPortStrategySucceedsGivenShellIsNotInstalled(t *testing.T) { }, ExecImpl: func(_ context.Context, _ []string, _ ...exec.ProcessOption) (int, io.Reader, error) { // This is the error that would be returned if the shell is not installed. - return 126, nil, nil + return exitEaccess, nil, nil + }, + } + + wg := NewHostPortStrategy("80"). + WithStartupTimeout(5 * time.Second). + WithPollInterval(100 * time.Millisecond) + + oldWriter := log.Default().Writer() + var buf bytes.Buffer + log.Default().SetOutput(&buf) + t.Cleanup(func() { + log.Default().SetOutput(oldWriter) + }) + + err = wg.WaitUntilReady(context.Background(), target) + require.NoError(t, err) + + require.Contains(t, buf.String(), "Shell not executable in container, only external port validated") +} + +func TestHostPortStrategySucceedsGivenShellIsNotFound(t *testing.T) { + listener, err := net.Listen("tcp", "localhost:0") + require.NoError(t, err) + defer listener.Close() + + rawPort := listener.Addr().(*net.TCPAddr).Port + port, err := nat.NewPort("tcp", strconv.Itoa(rawPort)) + require.NoError(t, err) + + target := &MockStrategyTarget{ + HostImpl: func(_ context.Context) (string, error) { + return "localhost", nil + }, + InspectImpl: func(_ context.Context) (*types.ContainerJSON, error) { + return &types.ContainerJSON{ + NetworkSettings: &types.NetworkSettings{ + NetworkSettingsBase: types.NetworkSettingsBase{ + Ports: nat.PortMap{ + "80": []nat.PortBinding{ + { + HostIP: "0.0.0.0", + HostPort: port.Port(), + }, + }, + }, + }, + }, + }, nil + }, + MappedPortImpl: func(_ context.Context, _ nat.Port) (nat.Port, error) { + return port, nil + }, + StateImpl: func(_ context.Context) (*types.ContainerState, error) { + return &types.ContainerState{ + Running: true, + }, nil + }, + ExecImpl: func(_ context.Context, _ []string, _ ...exec.ProcessOption) (int, io.Reader, error) { + // This is the error that would be returned if the shell is not found. + return exitCmdNotFound, nil, nil }, } @@ -505,6 +563,15 @@ func TestHostPortStrategySucceedsGivenShellIsNotInstalled(t *testing.T) { WithStartupTimeout(5 * time.Second). WithPollInterval(100 * time.Millisecond) + oldWriter := log.Default().Writer() + var buf bytes.Buffer + log.Default().SetOutput(&buf) + t.Cleanup(func() { + log.Default().SetOutput(oldWriter) + }) + err = wg.WaitUntilReady(context.Background(), target) require.NoError(t, err) + + require.Contains(t, buf.String(), "Shell not found in container") } From fa560fb4a64b817ca9166f23de4b72774d26e97d Mon Sep 17 00:00:00 2001 From: Steven Hartland Date: Thu, 19 Sep 2024 18:23:52 -0400 Subject: [PATCH 5/5] fix(mssql): bump Docker image version (#2786) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * chore: disable mssql tests Disable all mssql tests as the container is currently crashing, see #2785 * fix: use valid MSSQL image --------- Co-authored-by: Manuel de la Peña --- modules/mssql/examples_test.go | 2 +- modules/mssql/mssql.go | 2 +- modules/mssql/mssql_test.go | 32 +++++--------------------------- 3 files changed, 7 insertions(+), 29 deletions(-) diff --git a/modules/mssql/examples_test.go b/modules/mssql/examples_test.go index f5e7ebd04d..8c1f2c0cac 100644 --- a/modules/mssql/examples_test.go +++ b/modules/mssql/examples_test.go @@ -16,7 +16,7 @@ func ExampleRun() { password := "SuperStrong@Passw0rd" mssqlContainer, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-RTM-GDR1-ubuntu-20.04", + "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", mssql.WithAcceptEULA(), mssql.WithPassword(password), ) diff --git a/modules/mssql/mssql.go b/modules/mssql/mssql.go index 57f634c02c..17337bf85b 100644 --- a/modules/mssql/mssql.go +++ b/modules/mssql/mssql.go @@ -44,7 +44,7 @@ func WithPassword(password string) testcontainers.CustomizeRequestOption { // Deprecated: use Run instead // RunContainer creates an instance of the MSSQLServer container type func RunContainer(ctx context.Context, opts ...testcontainers.ContainerCustomizer) (*MSSQLServerContainer, error) { - return Run(ctx, "mcr.microsoft.com/mssql/server:2022-CU10-ubuntu-22.04", opts...) + return Run(ctx, "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", opts...) } // Run creates an instance of the MSSQLServer container type diff --git a/modules/mssql/mssql_test.go b/modules/mssql/mssql_test.go index 602778f8a0..737c97414e 100644 --- a/modules/mssql/mssql_test.go +++ b/modules/mssql/mssql_test.go @@ -17,7 +17,7 @@ func TestMSSQLServer(t *testing.T) { ctx := context.Background() ctr, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-CU10-ubuntu-22.04", + "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", mssql.WithAcceptEULA(), ) testcontainers.CleanupContainer(t, ctr) @@ -46,7 +46,7 @@ func TestMSSQLServerWithMissingEulaOption(t *testing.T) { ctx := context.Background() ctr, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-CU10-ubuntu-22.04", + "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", testcontainers.WithWaitStrategy( wait.ForLog("The SQL Server End-User License Agreement (EULA) must be accepted")), ) @@ -65,7 +65,7 @@ func TestMSSQLServerWithConnectionStringParameters(t *testing.T) { ctx := context.Background() ctr, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-CU10-ubuntu-22.04", + "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", mssql.WithAcceptEULA(), ) testcontainers.CleanupContainer(t, ctr) @@ -95,7 +95,7 @@ func TestMSSQLServerWithCustomStrongPassword(t *testing.T) { ctx := context.Background() ctr, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-CU10-ubuntu-22.04", + "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", mssql.WithAcceptEULA(), mssql.WithPassword("Strong@Passw0rd"), ) @@ -119,7 +119,7 @@ func TestMSSQLServerWithInvalidPassword(t *testing.T) { ctx := context.Background() ctr, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-CU10-ubuntu-22.04", + "mcr.microsoft.com/mssql/server:2022-CU14-ubuntu-22.04", testcontainers.WithWaitStrategy( wait.ForLog("Password validation failed")), mssql.WithAcceptEULA(), @@ -128,25 +128,3 @@ func TestMSSQLServerWithInvalidPassword(t *testing.T) { testcontainers.CleanupContainer(t, ctr) require.NoError(t, err) } - -func TestMSSQLServerWithAlternativeImage(t *testing.T) { - ctx := context.Background() - - ctr, err := mssql.Run(ctx, - "mcr.microsoft.com/mssql/server:2022-RTM-GDR1-ubuntu-20.04", - mssql.WithAcceptEULA(), - ) - testcontainers.CleanupContainer(t, ctr) - require.NoError(t, err) - - // perform assertions - connectionString, err := ctr.ConnectionString(ctx) - require.NoError(t, err) - - db, err := sql.Open("sqlserver", connectionString) - require.NoError(t, err) - defer db.Close() - - err = db.Ping() - require.NoError(t, err) -}