# Unit tests first, then end-to-end tests against a real Garage
# container via testcontainers-go. Merged into one job so the Go
# install + module cache are shared and a unit-test failure
# short-circuits before paying the ~150 MB Garage image pull.
#
# Order: install_go → install_cacher (built from source) → cacher_init
# → cache_gomod → test → docker_start → cache_garage_image →
# test_e2e.
#
# Dogfoods cacher (built fresh from source — this manifest is the
# regression test for the binary it produces) to cache:
# * ~/go/pkg/mod, keyed on sha256(go.sum) — biggest win, the docker
# SDK transitives are heavy.
# * The Garage docker image, via `cacher docker download --pull`
# which on miss falls back to `docker pull` and seeds S3.
# Go tarball itself isn't cached: cacher has to be built first, which
# needs Go, so chicken-and-egg. ~50MB curl is acceptable.
image: ubuntu/noble
packages:
- curl
- ca-certificates
- docker.io
secrets:
- 7dde4219-0783-4581-a67d-c94749de3600 # ~/.s3-cache-key-id
- 0e5b3530-6f19-4f30-9b73-9339dd382e46 # ~/.s3-cache-key-secret
sources:
- https://git.srht.bigb.es/~bigbes/ci-cacher
environment:
GO_VERSION: "1.26.3"
PATH: /home/build/.local/go/bin:/home/build/.local/bin:/usr/local/bin:/usr/bin:/bin
# Keep in sync with internal/testutil/garage/container.go const Image.
GARAGE_IMAGE: "dxflrs/garage:v2.3.0"
# No Ryuk reaper — the VM is torn down at job end, so the reaper
# container only adds startup logs we don't need.
TESTCONTAINERS_RYUK_DISABLED: "true"
submitter:
git.sr.ht:
enabled: true
allow-refs:
- refs/heads/master
- "refs/tags/*"
tasks:
- install_go: |
GO_TARBALL="go${GO_VERSION}.linux-amd64.tar.gz"
mkdir -p ~/.local
curl -sSL "https://go.dev/dl/$GO_TARBALL" -o "/tmp/$GO_TARBALL"
tar -xz -C ~/.local -f "/tmp/$GO_TARBALL"
rm "/tmp/$GO_TARBALL"
go version
- install_cacher: |
# Build from source so we exercise the binary this PR/branch
# actually produces — not the previously-published release.
mkdir -p ~/.local/bin
cd ci-cacher
go build -o ~/.local/bin/cacher .
cacher version
- cacher_init: |
cacher init \
--endpoint https://s3.bigb.es \
--region garage \
--bucket docker-cache \
--prefix ci-cacher/deps \
--key-file ~/.s3-cache-key-id \
--secret-file ~/.s3-cache-key-secret
- cache_gomod: |
# Cache ~/go/pkg/mod keyed by sha256(go.sum). A go.sum change
# invalidates automatically; otherwise both `go test` and the e2e
# variant (testcontainers + docker SDK transitives) hit the cache
# and skip proxy.golang.org entirely.
GOSUM_HASH=$(sha256sum ci-cacher/go.sum | cut -c1-16)
KEY="gomod/${GOSUM_HASH}.tar.gz"
if cacher download "$KEY" /tmp/gomod.tar.gz; then
mkdir -p ~/go
tar -xzf /tmp/gomod.tar.gz -C ~/go
else
cd ci-cacher && go mod download && cd ..
tar -czf /tmp/gomod.tar.gz -C ~/go pkg/mod
cacher upload "$KEY" /tmp/gomod.tar.gz
fi
rm -f /tmp/gomod.tar.gz
- test: |
cd ci-cacher
go test ./...
- docker_start: |
sudo systemctl start docker
sudo usermod -aG docker build
sudo chmod 666 /var/run/docker.sock
docker version
- cache_garage_image: |
# Key derived from the image ref so a version bump invalidates
# the cache automatically: dxflrs/garage:v2.3.0 → dxflrs-garage-v2.3.0
KEY="docker/$(echo "$GARAGE_IMAGE" | tr '/:' '-').tar.zst"
cacher docker download "$KEY" "$GARAGE_IMAGE" --pull
docker images "$GARAGE_IMAGE"
- test_e2e: |
cd ci-cacher
go test -tags=e2e -timeout=10m ./...