Context
When building docker images, it is desirable to produce images as a smaller as possible. That brings a lot of different benefits, among others:
- Less space used in the Container Registry and your local cache.
- Less traffic network and wait time when deploying the image.
But the languages and frameworks usually require a lot of development dependencies, which increases the overall size of the image. A neat alternative then, is to take advantage of multi-stage builds
Implementation
For this example, let’s assume you are a building a golang
project that produces a binary and that you have a standard Makefile
that invokes the go build
command under the hood, as shown below:
FROM golang:1.16 as builder
WORKDIR /app
COPY . .
RUN make build
FROM alpine:latest
COPY --from=builder /public/<binary_name> /usr/local/bin/
CMD ["<binary_name>"]
What makes this works is the COPY
command, through the use of the --from
option that allows to specify the source location to a previous build stage instead of the docker context sent by the user.
The above Dockerfile
can be build as follows:
docker build -t binary:latest .