Lighten Your Docker Images

Most Docker images originate from the scratch image. For example, Debian uses the scratch image as a base and adds the necessary files and architecture.

FROM scratch

ADD debian-buster-10.3.tar.xz /

CMD ["/bin/bash"]

So, technically, if we want a small image, we can start with the scratch image and only include the files and binaries we need. This brings us to the basics of an app:

  • Compiled source code
  • Dependencies
  • Language runtime

Distroless

This is exactly what Google does with Distroless images. Google created an open-source tool called Bazel to build these images. In the following sections, we’ll see how to build a Distroless image and use it. Distroless container are minimal that contain only your app and its runtime dependencies.

VM

alt text

Dockerfile

First, you need to understand and practice writing Dockerfiles.

FROM gcr.io/distroless/go:1.16
ADD app /
CMD ["/app"]

The image don’t have shells so you need to use the CMD/ENTRYPOINT in vector mode CMD ["app"] not CMD "app" instruction to run the app. By doing this docker bypass the shell and run the app directly via an exec syscall, which is handled by the kernel.

what is exec syscall? in Unix system exec is used to execute a new program. It replaces the current process with a new process.

Docker also supports multi-stage builds, which help optimize the image size.

FROM golang:1.16 as builder
WORKDIR /src
COPY . .
RUN go build -o /app

FROM gcr.io/distroless/go:1.16
COPY --from=builder /app /
CMD ["/app"]

Bazel