Skip to content

Distributing your images

There would be little point in going through all the trouble of making your analyses reproducible if you can't distribute them to others. Luckily, sharing Docker containers is extremely easy, and can be done in several ways. One of the more common ways to share Docker images is through container registries and repositories.

For example, a Docker registry is a service that stores Docker images, which could be hosted by a third party, publicly or privately. One of the most common registries is Docker Hub, which is a registry hosted by Docker itself. A repository, on the other hand, is a collection of container images with the same name but different tags, i.e. versions. For example, ubuntu:latest or ubuntu:20.04. Repositories are stored in registries.

Note

Remember that we now have some clashing nomenclature between Git repositories (which we covered in the Git tutorial) and container repositories, so be aware of which one you're talking about!

There are many registries out there, but here are some that might be of interest to you who are taking this course:

Docker Hub#

The most common registry is probably Docker Hub, which lets you host unlimited public images and one private image for free (after which they charge a small fee). Let's see how it's done!

  1. Register for an account on Docker Hub.

  2. Use docker login -u your_dockerhub_id to login to the Docker Hub registry.

  3. When you build an image, tag it with -t your_dockerhub_id/image_name, rather than just image_name.

  4. Once the image has been built, upload it to Docker Hub with docker push your_dockerhub_id/image_name.

  5. If another user runs docker run your_dockerhub_id/image_name the image will automatically be retrieved from Docker Hub. You can use docker pull for downloading without running.

If you want to refer to a Docker image in for example a publication, it's very important that it's the correct version of the image. You can do this by adding a tag to the name like this docker build -t your_dockerhub_id/image_name:tag_name.

Tip

On Docker Hub it is also possible to link to your Bitbucket or GitHub account and select repositories from which you want to automatically build and distribute Docker images. The Docker Hub servers will then build an image from the Dockerfile in your Git repository and make it available for download using docker pull. That way, you don't have to bother manually building and pushing using docker push.

Using GitHub Container Registry (GHCR)#

  1. Create a GitHub Personal Access Token, it is necessary to authenticate when pushing your container image to GitHub Container Registry:
    • Go to your GitHub account -> Settings -> Developer settings -> Personal Access Tokens -> Generate new token.
    • Select the necessary permissions (write:packages, read:packages, etc.) and generate the token.

  2. Login to GitHub Container Registry via the docker login Docker command: Use the GitHub CLI or Docker to authenticate.

    echo "<your-token>" | docker login ghcr.io -u <your-username> --password-stdin
    
  3. Push the Image to GitHub Container Registry:

    docker push ghcr.io/<your-username>/<image-name>:<tag>
    

  4. Manage Images on GitHub:
    Once uploaded, the container image will appear under the Packages section of your GitHub repository, where you can manage access, visibility, and versioning.

Alternative: Using GitHub Actions to Build and Push Images Automatically

You can automate this process by using GitHub Actions to build and push Docker images whenever there’s a change in your repository.

Here’s a simple GitHub Actions workflow (.github/workflows/docker-publish.yml) to build and push an image:

name: Docker Image CI

on:
push:
    branches:
    - main

jobs:
build:
    runs-on: ubuntu-latest

    steps:
    - name: Checkout code
        uses: actions/checkout@v2

    - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v1

    - name: Login to GitHub Container Registry
        run: echo "${ secrets.GITHUB_TOKEN }" | docker login ghcr.io -u ${ github.actor } --password-stdin

    - name: Build and push Docker image
        run: |
        docker build -t ghcr.io/${ github.repository }/my-image:latest .
        docker push ghcr.io/${ github.repository }/my-image:latest
/!\ Think to double the brackets { (impossible here du to jinja...) In this workflow:
• GitHub builds the Docker image every time a commit is pushed to the main branch.
• The image is automatically pushed to GitHub Container Registry.

Quick recap

In this section we've learned:

  • How container registries and repositories work
  • How to use Docker Hub to share Docker images