Best practices for building docker images with GitLab CI

Using a generic .gitlab-ci.yml file that you can drop in

March 4, 2019

At CALLR, we have been using GitLab for quite a while. We are also using more and more Docker containers. In this post, I’ll show you how we build docker images with a simple .gitlab-ci.yml file.

Let’s not waste any time.

The GitLab CI yaml configuration file

Here is a .gitlab-ci.yml file that you can drop in directly without any modification in a project with a working Dockerfile.

It will:

  • build a docker image for each git commit, tagging the docker image with the commit SHA
  • tag the docker image “latest” for the “master” branch
  • keep in sync git tags with docker tags

All docker images will be pushed to the GitLab registry containing the project

Best practices

  1. Do not use “latest” nor “stable” images when using a CI. Why? Because you want reproducibility. You want your pipeline to work in 6 month. Or 6 years. Latest images will break things. Always target a version. Hence image: docker:18 here.

  2. To speed-up your docker builds, pull the “latest” image ($CI_REGISTRY_IMAGE:latest) before building , and then build with --cache-from $CI_REGISTRY_IMAGE:latest. This will make sure the GitLab runner has the latest image and can leverage layer caching. Chances are you did not change all layers, so the build process will be very fast.

  3. In the push jobs, tell GitLab not to clone the source code with GIT_STRATEGY: none. Since we are just playing with docker pull/push, we do not need the source code. This will speed things up as well.

  4. Finally, keep your Git tags in sync with your Docker tags. If you have not automated this, you have probably found yourself in the situation of wondering “which git tag is this image again?”. No more. Use GitLab “tags” pipelines.

Further reading