Hosting a local container registry
How to host a local container registry
Host your own Container Registry Locally
Why would you want to?? In production, you wouldn’t but if you are doing some local homelab stuff or developing, you might have cases where having a local repository makes alot of sense or helps in your workflows.
Install docker and docker compose
Starting with a fresh install of Ubuntu Server 22.04…
From a terminal window on the server, let’s install docker and docker-compose
# always be sure to update linux before installing these components, just good practice
sudo apt update
sudo apt upgrade -y
# now let's install docker
sudo apt install docker.io
# next install docker-compose
sudo apt install docker-compose
Verify the installation by checking for version output with the following commands
docker version
docker-compose version
Run the registry, a container from docker
Make a directory to store our configuration
mkdir ~/registry
cd ~/registry
mkdir data
Make a docker-compose.yml file
nano docker-compose.yml
Yml file contents
version: '3'
services:
registry:
image: registry:2
ports:
- "5000:5000"
environment:
REGISTRY_STORAGE_FILESYSTEM_ROOTDIRECTORY: /data
volumes:
- ./data:/data
Stand it up
sudo docker-compose up -d
Stand up a reverse proxy with a valid cert pointing to your registry
You can do this using starting with nginx, setting up the reverse proxy, adding a certificate, probably self-signed, then going through the steps of trusting that certificate so that when we later run the docker command to push/pull, the certificate is trusted, but we aren’t going to do all that.
Here we will be using a project from medic on github that uses the local-ip.co project which is a creative way to provide a cert for free that is trusted
Clone the repository
git clone https://github.com/medic/nginx-local-ip.git
Stand up the nginx proxy
sudo APP_URL=http://192.168.1.235:5000 docker-compose up
At this point you should have nginx listening, however your DNS won’t be able to find “https://{ip}.my.local-ip.co/”, locally there are a couple of easy options to fix this, you could update your hostfile if you are using windows or in my case I am adding an entry in PFSense in the DNS Resolver so that when this host is queried, it will return the IP of my local machine.
When I browse to “https://192-168-1-235.my.local-ip.co/v2”, I should get a respose: ![[Pasted image 20230217065923.png]]
[!note] Note I will be using “192-168-1-235.my.local-ip.co” throughout the rest of this blog, please be sure and change this to match your environment
Test pushing an image to the repository
Standup an ubuntu container so we make a small change, commit it and push it to our local repository
sudo docker run -t -i ubuntu /bin/bash
This will open an interactive shell, let’s add file in our container
touch /testingademo
exit
Commit the change to the image
sudo docker commit $(sudo docker ps -lq) test-image
Tag the image
sudo docker tag test-image 192-168-1-235.my.local-ip.co/test-image
[!note] Note You can setup authentication on your local repository, I chose not to do this for this demo. For a good document on how you could setup the auth, DigitalOcean has a good posting on this at https://www.digitalocean.com/community/tutorials/how-to-set-up-a-private-docker-registry-on-ubuntu-20-04
Push the image to the repository
sudo docker push 192-168-1-235.my.local-ip.co/test-image
Browsing your registry with the docker-registry-browser from klausmeyer
- https://github.com/klausmeyer/docker-registry-browser/blob/master/docs/README.md
- https://hub.docker.com/r/klausmeyer/docker-registry-browser/
sudo docker run --name registry-browser -e DOCKER_REGISTRY_URL=https://192-168-1-235.my.local-ip.co -p 8080:8080 klausmeyer/docker-registry-browser
You can now view this site in the browser: http://{ip}:8080/ (e.g. http://192.168.1.235:8080)
Pulling the image from the local repository
Here we will quickly pull the image and verify it is the image we had pushed earlier just to come full circle
Pull the image
sudo docker pull 192-168-1-235.my.local-ip.co/test-image
Run the image, immediately launching a shell into the container
sudo docker run -it 192-168-1-235.my.local-ip.co/test-image /bin/bash
Do a directory listing to verify the “testingademo” item exists
ls
Exit the shell You have just completed standing up a local container repository!
exit