Multi architecture builds of Docker images
4 minutes read
tech docker

"Build once and run anywhere" sounds like the perfect way to explain Docker to the newbies. But unfortunately this is not true always. Docker images are architecture specific. You can't run an image built for amd64 architecture on a arm64 machine. Let's understand the problem here,

Why do we need different images for different architectures?

There are a few reasons why we need to have different Docker images for different architectures:

  • Differences in instruction sets: For example, an x86_64 machine has a different instruction set than an ARM machine. This means that the same Docker image cannot be run on both architectures without being compiled for each architecture.
  • Differences in hardware capabilities: For example, an ARM machine may have less RAM than an x86_64 machine. This means that a Docker image that is designed to run on an ARM machine may not be able to run on an x86_64 machine without being modified.
  • Differences in operating systems: For example, a Docker image that is designed to run on Linux cannot be run on Windows without being modified.

By creating separate Docker images for different architectures and operating systems, we can ensure that our images are portable and that they can be run on a wide variety of platforms. This makes it easier for us to deploy our applications and to reach a wider audience.

Is this a common practice? Does all images are built for multiple architectures?

Generally, the web applications (that most of us work on) aren't built for multiple architectures. Because most of these are typically servers and they are built for amd64 architecture because most of the servers are amd64 architecture.

But, if you are building an application for IoT devices, then you need to build for multiple architectures. Because IoT devices are built for different architectures. Example, Raspberry Pi is built for arm64 architecture. So, if you are building an application for Raspberry Pi, then you need to build for arm64 architecture.

Applications like Redis, MySQL, nginx etc. are built for multiple architectures. Because these applications are used in servers and IoT devices. So, they need to be built for multiple architectures.

How to build a Docker image for multiple architectures?

Docker has a feature called buildx which allows you to build images for multiple architectures. You can use the buildx command to build images for multiple architectures.

docker buildx build --platform linux/amd64,linux/arm64 -t <image-name> .

This command will build the image for both amd64 and arm64 architectures. You can also build for other architectures like arm/v7, arm/v6, s390x, ppc64le etc.

How to run an architecture specific docker image?

In general, docker pulls in the image based on the architecture. For example, if you are running on Mac M1/M2(apple processors) docker automatically pulls in arm64 images. If you are running on a Linux machine, docker pulls in amd64 images. However, if you want to run a specific architecture image, you can do so by specifying the platform.

docker run --platform linux/arm64 <image-name>

or in the docker base image you can specify the platform.

FROM --platform=linux/arm64 alpine

Note: Likely the images won't be working as expected in a different architecture. So, it is not a good idea to run an image built for amd64 architecture on a arm64 machine.

Prasanna is a full stack web developer, with exposure to various programming languages. Uses mostly Java, Javascript these days and got ~13 years of architecting and coding enterprise software solutions.