Docker has revolutionized the way applications are deployed by providing lightweight, portable containers. However, one common challenge developers face is managing the size of Docker images. Large images not only take up more disk space but also slow down deployments and increase the time to push/pull images. Fortunately, there are several strategies to minimize the size of Docker images. Below are some practical tips to help you reduce the size of your Docker images.
1. Use Official Minimal Base Images
You can choose the right base image. Official images like alpine
and debian-slim
are lightweight alternatives to larger images like ubuntu
.
For example, alpine
is just 5 MB in size, while ubuntu
can be over 100 MB.
# From an Alpine-based image
FROM node:alpine
# From a slim Debian-based image
FROM python:3.9-slim
2. Use Multi-stage Builds
Multi-stage builds are a powerful feature that allow you to build your application in one stage and copy only the necessary artifacts to the final image. This is especially useful for compiled languages like Go or Java, where you need to install heavy build tools in the first stage but not in the final image.
# First stage: Build stage
FROM golang:alpine AS build
WORKDIR /app
COPY . .
RUN go build -o main .
# Second stage: Run stage
FROM alpine:latest
WORKDIR /app
COPY --from=build /app/main .
CMD ["./main"]
In the above example, the final image only contains the compiled binary, not the Go compiler or any build dependencies, greatly reducing the size of the image.
You can use the same method to create the docker images for other types of applications.
3. Minimize the building layers
Every RUN
, COPY
, or ADD
command in a Dockerfile creates a new layer. By combining commands, you can reduce the number of layers and therefore the size of the image.
# Before: Multiple layers
RUN apt-get update
RUN apt-get install -y curl
After minimizing layers, command will be look like below.
# After: Combined layers
RUN apt-get update && apt-get install -y curl
4. Clean Up Temporary Files
After installing packages, temporary files like cache files, downloaded dependencies, and package manager lists can consume unnecessary space. It’s a good practice to remove them in the same RUN
statement where they were created.
RUN apt-get update && apt-get install -y \
build-essential \
&& rm -rf /var/lib/apt/lists/*
In the case of Alpine, use:
RUN apk add --no-cache gcc musl-dev
Here, the --no-cache
flag prevents caching index files, saving extra space.
5. Use .dockerignore
File
Just like .gitignore
, Docker has a .dockerignore
file to exclude files and directories from being copied into the image. This prevents unnecessary files (e.g., logs, config files, or source code that doesn’t need to be in the final image) from bloating your image.
node_modules
*.log
.git
Ensure that you only include the files that are absolutely necessary for your application to run.
6. Use Smaller Base Dependencies
Often, Docker images are larger because they install large dependencies or unnecessary tools. Use slimmer or custom-built versions of dependencies and avoid unnecessary utilities that aren’t needed in production.
For example, instead of installing a full-featured web server, consider using something like nginx:alpine
, which is a small version of Nginx.