This year, I have been working on learning rust and as part of that process I am building a static site generator named Shazam. At the moment, I am using a couple of other non-rust projects for some of the features until I can build them out in Rust.

Using Docker to manage all of these services, seemed like the easiest way to get going quickly if someone wants to use the project so I published a container image to Docker Hub with everything packed in.

In this post, I will share what I learned on how to publish a container image to Docker Hub.

Software Versions

The following software versions were used in this post.

  • Docker Community Edition - 20.10.21
  • Ubuntu - 22.04.1 LTS

Docker Hub Credentials

Firstly, you need to get your Docker Hub account setup and generate an API key. To generate an API key browse to:

Create an access token with Read, Write and Delete permissions.

Take note of the API key, once you close the window, you will no longer be able to see the API key.

Save the credentials in your ~/.zshrc file.


Don't forget to source ~/.zshrc the file to load the variables into your environment.

Now login to Docker Hub with the docker login command.

I could not find a way to make the docker login command automatically use these environment variables. If I do, I will update this post. If you know of a way, please feel free to reach out to me.

This will create the /home/bradmin/.docker/config.json credential file which will be used for future logins.

Docker Image Build

Alright, now we can build the image. The below Dockerfile Builds the image, first by creating a builder image to compile and gather all the binaries. The binaries are then copied to the final image that is released. This results in a much smaller image that we publish to Docker hub.

FROM rust:1.64-alpine as builder


RUN apk add curl protoc musl-dev gzip git

# tailwind
RUN curl -sLO \
  && chmod +x tailwindcss-linux-x64 \
  && mv tailwindcss-linux-x64 tailwindcss

# reflex
RUN curl -sLO \
  && tar -xvf reflex_linux_amd64.tar.gz \
  && chmod +x reflex_linux_amd64/reflex \
  && mv reflex_linux_amd64/reflex reflex

# overmind
RUN curl -sLO \
  && gunzip overmind-v2.3.0-linux-amd64.gz \
  && chmod +x overmind-v2.3.0-linux-amd64 \
  && mv overmind-v2.3.0-linux-amd64 overmind

# shazam
RUN git clone \
  && cd shazam \
  && cargo build --release


FROM alpine:3.16.2

RUN apk add tmux

COPY --from=builder /opt/shazam/target/release/shazam /opt/shazam
COPY --from=builder /opt/tailwindcss /opt/tailwindcss
COPY --from=builder /opt/reflex /opt/reflex
COPY --from=builder /opt/overmind /opt/overmind

RUN chown -R root:root /opt/

Use the docker image build command to build the image from the Dockerfile.

docker image build --file Dockerfile --tag bwks/shazam:v0.1.20 .

The above command, builds the image, also tagging it with the parameters that map to the Docker hub repository. The details of the tag are as follows:

  • bwks - The Docker hub account
  • shazam - The name of the Repository
  • v0.1.20 - The image tag

You can use the docker image ls command to see the size of the image.

docker image ls

REPOSITORY    TAG           IMAGE ID       CREATED        SIZE
bwks/shazam   v0.1.20       a28ee56bd31a   27 hours ago   135MB

A not-too-shabby 135MB. Pretty good considering the builder image is around 700MB.

Docker Image Publish

The image can be published to Docker Hub with the docker image push command.

docker image push bwks/shazam:v0.1.20

Once the upload is complete, you can now browse to the repository and see that the image is published.


And thats it, you now have a container image published to Docker hub. Party on you crazy bunch of savages 🤘

# docker