How to Build a Multi-Arch Docker Image in Bitbucket Pipelines
Enable the docker service, register QEMU, and drive Buildx to push a multi-platform image from one step.
Add the built-in docker service for a daemon, install QEMU emulators, create a Buildx builder, then docker buildx build --platform ... --push.
Buildx with the docker service
The docker service gives a daemon; QEMU plus Buildx build both platforms and push.
pipelines:
default:
- step:
name: Build multi-arch
image: atlassian/default-image:4
services:
- docker
script:
- echo "$DOCKER_PASSWORD" | docker login -u "$DOCKER_USER" --password-stdin
- docker run --privileged --rm tonistiigi/binfmt --install all
- docker buildx create --use
- docker buildx build --platform linux/amd64,linux/arm64 -t myorg/app:$BITBUCKET_COMMIT --push .Gotchas
- You must add
- dockertoservices:or thedockercommands cannot reach a daemon. - QEMU registration plus emulated arm64 builds are memory-hungry - set a larger step
size: 2x. - Buildx pushes the manifest directly; a multi-arch image cannot be loaded into the local daemon.
Verify it actually works
Bitbucket validates bitbucket-pipelines.yml on push, and a schema error disables the pipeline rather than failing a build, which can look like nothing happened at all.
# validate before pushing
curl -X POST -H "Content-Type: application/x-yaml" \
--data-binary @bitbucket-pipelines.yml \
https://api.bitbucket.org/2.0/repositories/<workspace>/<repo>/pipelines/validate
# confirm which pipeline definition matched
# Pipelines -> the run -> "Configuration" tabConstraints that catch people out
- Each step runs in a fresh container. Nothing persists between steps unless it is declared as an artifact or a cache.
- The default memory allocation per step is limited, and service containers share that budget, so adding a database service can push a previously passing build into an out-of-memory failure.
- Only branches with a matching
branches:definition run; a push to an unmatched branch silently runs nothing. - Artifacts are passed forward only to later steps in the same pipeline, not between pipelines.