This is the third post in a series on making smaller Docker images. In the first post I talked about how to create smaller images by writing better Dockerfiles. In the second post I talked about how to squash layers using docker-squash to make smaller images. These methods are great but they won’t help us if we choose large base images to start with!
Let’s look at the example from the second post, the standard
python image on Docker hub. If we look at the Dockerfile for this image, as of this writing, it’s based on a Debian jessie base image.
FROM buildpack-deps:jessie # ensure local python is preferred over distribution python ENV PATH /usr/local/bin:$PATH ...
buildpack-deps:jessie image includes a full Debian jessie distribution install and is quite large.
~$ docker images buildpack-deps:jessie REPOSITORY TAG IMAGE ID CREATED SIZE buildpack-deps jessie 3b84923989a0 3 weeks ago 614 MB
We can see here that it’s 614MB to start. Even squashing it isn’t going to help much because there’s just a lot of data in the base distribution.
Alpine Linux is a distribution of Linux that is built to be very small for the base install. But even though it’s small it still has a nice package repository with lots of packages. It also has a tool much like
yum to easily install those packages.
~$ docker images alpine:3.6 REPOSITORY TAG IMAGE ID CREATED SIZE alpine 3.6 a41a7446062d 5 days ago 3.966 MB
It’s only 3.96 MB. That’s a huge difference from the 600+ Debian jessie image. Many standard Docker images conveniently have an Alpine Linux version. Usually it has an
-alpine suffix. Let’s look at our python example.
~$ docker images python:2.7.13-alpine REPOSITORY TAG IMAGE ID CREATED SIZE python 2.7.13-alpine 3dd614730c9c 4 days ago 72.02 MB
The Python VM takes up about 72MB but that’s still much better than the 670 MB for the Debian based python image.
Building Images with Alpine
You can build images with Alpine and install Alpine packages using the
apk tool in your Dockerfile. You might do something like the following to get a checkout of a git repo.
FROM alpine:3.6 RUN apk add --update git && \ git clone https://github.com/example/myrepo.git && \ rm myrepo/.git && \ apk del git && \ rm -rf /var/cache/apk/* CMD ['/myrepo/myapp']
You can view the available packages for Alpine at https://pkgs.alpinelinux.org/