Creating Docker images with M1 Macs

I ran into an issue with my Dockerfile when using it on a Linux machine, setting a platform fixed the issue

We recently ran into an issue deploying a Ruby on Rails application onto AWS using Docker. The issue turned out to be the Mac I was creating the image on! Whilst this might be a common gotcha to many, it tripped me up so I wanted to write up a quick post about it, in the hope it helps someone out.

I wanted to create an image, put it onto the Elastic Container Registry, and use it as the basis for my application.

The Dockerfile was pretty bare bones, it grabbed FROM ruby:3.1.0-slim did some Ruby stuff, then tried to start the server.

The error I was getting anytime anything tried to run the image on AWS was exec /usr/bin/entrypoint.sh: exec format error.

What this means is that Docker had got through the Dockerfile, and was ready to execute what I’d defined inside bin/entrypoint.sh.

The contents of my entrypoint.sh were a simple bash script, which worked locally.

Doing some searching online, and with the help of AWS support, we narrowed it down to some potential issues;

  • A genuine issue with the script (not the case, it worked locally)
  • Permissions with the script (not the case, it was chmod +x correctly)
  • Incorrect line endings (a common issue on Windows were different whitespace characters make their way into the script and Linux can’t understand them)
  • A different chipset being used (bingo!)

I was building the image on a Mac with an M1 chip inside it. I had wrongly thought that because Mac and Linux were largely compatible with each other, the different chip between my computer and AWS wouldn’t matter. Also I know very little about Docker and kind of thought it would work its magic regardless of chips.

The fix is to define the target platform in any FROM statements inside the Dockerfile. For example;

  FROM --platform=linux/amd64 ruby:3.1.0-slim

This says “Regardless of the system that is building this image, please build for the following platform”. In our case the important bit was amd64.

I hope this saves you a headache!


Recent posts View all

Web Dev

Creating draft posts in Jekyll

How to create and develop with draft posts in Jekyll

Ruby

Forcing a Rails database column to be not null

How you can force a table column to always have something in it with Rails