testcontainers-go
testcontainers-go copied to clipboard
[Bug]: .dockerignore not parsed in the same was a Docker does it
Testcontainers version
v0.35.0
Using the latest Testcontainers version?
Yes
Host OS
MacOS
Host arch
ARM
Go version
1.23.3
Docker version
Client:
Version: 27.4.0
API version: 1.47
Go version: go1.22.10
Git commit: bde2b89
Built: Sat Dec 7 10:35:43 2024
OS/Arch: darwin/arm64
Context: desktop-linux
Server: Docker Desktop 4.37.2 (179585)
Engine:
Version: 27.4.0
API version: 1.47 (minimum version 1.24)
Go version: go1.22.10
Git commit: 92a8393
Built: Sat Dec 7 10:38:33 2024
OS/Arch: linux/arm64
Experimental: false
containerd:
Version: 1.7.21
GitCommit: 472731909fa34bd7bc9c087e4c27943f9835f111
runc:
Version: 1.1.13
GitCommit: v1.1.13-0-g58aa920
docker-init:
Version: 0.19.0
GitCommit: de40ad0
Docker info
Client:
Version: 27.4.0
Context: desktop-linux
Debug Mode: false
Plugins:
ai: Ask Gordon - Docker Agent (Docker Inc.)
Version: v0.5.1
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-ai
buildx: Docker Buildx (Docker Inc.)
Version: v0.19.2-desktop.1
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-buildx
compose: Docker Compose (Docker Inc.)
Version: v2.31.0-desktop.2
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-compose
debug: Get a shell into any image or container (Docker Inc.)
Version: 0.0.37
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-debug
desktop: Docker Desktop commands (Beta) (Docker Inc.)
Version: v0.1.0
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-desktop
dev: Docker Dev Environments (Docker Inc.)
Version: v0.1.2
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-dev
extension: Manages Docker extensions (Docker Inc.)
Version: v0.2.27
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-extension
feedback: Provide feedback, right in your terminal! (Docker Inc.)
Version: v1.0.5
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-feedback
init: Creates Docker-related starter files for your project (Docker Inc.)
Version: v1.4.0
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-init
sbom: View the packaged-based Software Bill Of Materials (SBOM) for an image (Anchore Inc.)
Version: 0.6.0
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-sbom
scout: Docker Scout (Docker Inc.)
Version: v1.15.1
Path: /Users/adamvanderveer/.docker/cli-plugins/docker-scout
Server:
Containers: 7
Running: 6
Paused: 0
Stopped: 1
Images: 31
Server Version: 27.4.0
Storage Driver: overlayfs
driver-type: io.containerd.snapshotter.v1
Logging Driver: json-file
Cgroup Driver: cgroupfs
Cgroup Version: 2
Plugins:
Volume: local
Network: bridge host ipvlan macvlan null overlay
Log: awslogs fluentd gcplogs gelf journald json-file local splunk syslog
CDI spec directories:
/etc/cdi
/var/run/cdi
Swarm: inactive
Runtimes: io.containerd.runc.v2 runc
Default Runtime: runc
Init Binary: docker-init
containerd version: 472731909fa34bd7bc9c087e4c27943f9835f111
runc version: v1.1.13-0-g58aa920
init version: de40ad0
Security Options:
seccomp
Profile: unconfined
cgroupns
Kernel Version: 6.10.14-linuxkit
Operating System: Docker Desktop
OSType: linux
Architecture: aarch64
CPUs: 8
Total Memory: 15.35GiB
Name: docker-desktop
ID: 05f8db2c-6916-4cf0-b524-f7c8001c6c5f
Docker Root Dir: /var/lib/docker
Debug Mode: false
HTTP Proxy: http.docker.internal:3128
HTTPS Proxy: http.docker.internal:3128
No Proxy: hubproxy.docker.internal
Labels:
com.docker.desktop.address=unix:///Users/<REDACTED>/Library/Containers/com.docker.docker/Data/docker-cli.sock
Experimental: false
Insecure Registries:
hubproxy.docker.internal:5555
127.0.0.0/8
Live Restore Enabled: false
WARNING: daemon is not using the default seccomp profile
What happened?
I'm trying to use the build feature to build docker images for my tests on-the-fly. For this there is a dockerginore file that looks like this:
*
!lambda/**/*.go
!proto/**/*.go
!go.mod
!go.sum
There is a "main.go" in lambda/describedocument/cmd/main.go (content doesn't matter, could be simple hello world)
I have a Dockerfile that looks like this:
# Stage 1: Modules caching
FROM golang:1.23 AS modules
COPY go.mod go.sum /modules/
WORKDIR /modules
RUN go mod download
# Stage 2: Build our application code
FROM golang:1.23 AS builder
COPY --from=modules /go/pkg /go/pkg
COPY . /workdir
WORKDIR /workdir
RUN CGO_ENABLED=0 go build -o /bin/describedocument ./lambda/describedocument/cmd
# Stage 3: Final assembly
FROM gcr.io/distroless/static-debian12 AS describedocument
COPY --from=builder /bin/describedocument /
ENTRYPOINT ["/describedocument"]
I have a docker compose file that looks like this:
services:
describedocument:
platform: linux/amd64
build:
context: .
dockerfile: lambda/describedocument/Dockerfile
target: describedocument
ports:
- "8584:8080"
volumes:
- ./magefiles/aws-lambda-rie/aws-lambda-rie:/aws-lambda-rie
- $HOME/.aws/credentials:/root/.aws/credentials:ro
entrypoint: /aws-lambda-rie /describedocument
When i let docker compose build the docker image, it works. But when i let testcontainers-go build it, it will say in the build logs:
---> Running in d121e0b7b558
stat /workdir/lambda/describedocument/cmd: directory not found
---> Removed intermediate container d121e0b7b558
e2e_test.go:21:
Error Trace: /Users/adamvanderveer/Documents/Projects/github.com/crewlinker/openai/e2e_test.go:95
/Users/adamvanderveer/Documents/Projects/github.com/crewlinker/openai/e2e_test.go:21
Error: Received unexpected error:
create container: build image: The command '/bin/sh -c CGO_ENABLED=0 go build -o /bin/describedocument ./lambda/describedocument/cmd' returned a non-zero code: 1
Test: TestSmoke
--- FAIL: TestSmoke (0.35s)
When i double check this, the directory ./lambda/describedocument is indeed empty when building it with testcontainers. IF i change my dockerignore to look like this (and change nothing else):
*
!lambda/**/*.go
!lambda/describedocument/**/*.go
!lambda/describedocument/cmd/*.go
!proto/**/*.go
!go.mod
!go.sum
Test containers will build it correctly. So there is a difference between Docker and Testcontainers in how **/*.go is interpreted.
For completeness, this is how i'm testing it in Go:
package openai_test
import (
"context"
"fmt"
"os"
"path/filepath"
"testing"
"time"
"github.com/advdv/stdgo/stdlo"
"github.com/carlmjohnson/requests"
"github.com/docker/docker/api/types"
"github.com/docker/go-connections/nat"
"github.com/stretchr/testify/require"
"github.com/testcontainers/testcontainers-go"
"github.com/testcontainers/testcontainers-go/wait"
)
func TestSmoke(t *testing.T) {
ctx, req := setup(t)
require.NoError(t, req.BodyBytes([]byte(`{}`)).Post().Fetch(ctx))
_ = ctx
_ = req
}
type testLogConsumer struct{ testing.TB }
func (lc *testLogConsumer) Accept(l testcontainers.Log) {
lc.Logf("%s: %s", l.LogType, l.Content)
}
func setup(t *testing.T) (context.Context, *requests.Builder) {
t.Helper()
t.Parallel()
ctx, cancel := context.WithCancel(context.Background())
t.Cleanup(cancel)
wdir, hdir := stdlo.Must1(os.Getwd()), stdlo.Must1(os.UserHomeDir())
logConsumer := &testLogConsumer{t}
cwd, err := os.Getwd()
require.NoError(t, err)
fmt.Println(cwd)
container, err := testcontainers.GenericContainer(ctx, testcontainers.GenericContainerRequest{
ContainerRequest: testcontainers.ContainerRequest{
FromDockerfile: testcontainers.FromDockerfile{
Context: cwd,
Dockerfile: filepath.Join("lambda", "describedocument", "Dockerfile"),
BuildLogWriter: os.Stderr,
BuildOptionsModifier: func(ibo *types.ImageBuildOptions) {
// ibo.Platform = "linux/amd64"
ibo.Dockerfile = filepath.Join("lambda", "describedocument", "Dockerfile")
ibo.Target = "describedocument"
},
},
// Image: "openai-describedocument", // must be build beforehand, easiest is to run mage -v dev:serve at least once
ExposedPorts: []string{"8080/tcp"},
Files: []testcontainers.ContainerFile{
{
HostFilePath: stdlo.Must1(filepath.Abs(filepath.Join(wdir, "magefiles", "aws-lambda-rie", "aws-lambda-rie"))),
ContainerFilePath: "/aws-lambda-rie",
FileMode: 0o7777,
},
{
HostFilePath: stdlo.Must1(filepath.Abs(filepath.Join(hdir, ".aws", "credentials"))),
ContainerFilePath: "/root/.aws/credentials",
FileMode: 0o7777,
},
},
Env: map[string]string{
"AWS_REGION": "eu-central-1",
"AWS_PROFILE": "cl-ats",
},
Entrypoint: []string{"/aws-lambda-rie", "/describedocument"},
WaitingFor: wait.ForAll(
wait.ForLog("[INFO] (rapid) exec"),
wait.ForListeningPort(nat.Port("8080/tcp")).SkipInternalCheck(),
),
LogConsumerCfg: &testcontainers.LogConsumerConfig{
Opts: []testcontainers.LogProductionOption{testcontainers.WithLogProductionTimeout(10 * time.Second)},
Consumers: []testcontainers.LogConsumer{logConsumer},
},
},
Started: true,
})
testcontainers.CleanupContainer(t, container)
require.NoError(t, err)
ep, err := container.Endpoint(ctx, "")
require.NoError(t, err)
return ctx, requests.URL("http://" + ep + "/2015-03-31/functions/function/invocations").Post()
}
Relevant log output
Additional information
No response