Intro

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.

Note
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.

~/.zshrc
export DOCKER_USERNAME="<USERNAME>"
export DOCKER_PASSWORD="<API_KEY>"

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.

cmd
docker login -u $DOCKER_USERNAME -p $DOCKER_PASSWORD
Note
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.

Dockerfile
FROM rust:1.64-alpine as builder

WORKDIR /opt/

RUN apk add curl protoc musl-dev gzip git

# tailwind
RUN curl -sLO https://github.com/tailwindlabs/tailwindcss/releases/latest/download/tailwindcss-linux-x64 \
  && chmod +x tailwindcss-linux-x64 \
  && mv tailwindcss-linux-x64 tailwindcss

# reflex
RUN curl -sLO https://github.com/cespare/reflex/releases/latest/download/reflex_linux_amd64.tar.gz \
  && tar -xvf reflex_linux_amd64.tar.gz \
  && chmod +x reflex_linux_amd64/reflex \
  && mv reflex_linux_amd64/reflex reflex

# overmind
RUN curl -sLO https://github.com/DarthSim/overmind/releases/latest/download/overmind-v2.3.0-linux-amd64.gz \
  && 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 https://github.com/bwks/shazam.git \
  && 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.

cmd
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.

cmd
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.

cmd
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.

Outro

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

# docker