On your machines inside a VPN, there are use-cases where a private docker registry is handy especially if you want to have a customized image built for your stack.
The caveat is that docker automatically assumes that all your connections are encrypted via https . And that means you need to have domain to encrypt your traffic on https protocol. This guide will help you setup a registry without having a DNS and a valid SSL/TLS Certificate:
Ahm.. Ken there is already a Tutorial on docker official docs about creating a private registry
Deploying a registry server_You need to install Docker version 1.6.0 or newer. Running on localhost Start your registry: docker run -d -p 5000:5000…_docs.docker.com
The docker official docs are a good enough starting point when you want to learn the basics and the theory. However you will need to dig around if you want to make it registry work without a proper SSL Certificate and DNS.
Also my stuff are easy to follow and copy paste-able
Since our machines are already inside VPN using a self signed certificate is good enough method for securing your Docker Registry.
sudo apt-get install \ apt-transport-https \ ca-certificates \ curl \ software-properties-common
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
sudo apt-key fingerprint 0EBFCD88
sudo apt-get update
sudo apt-get install docker-ce
# Important# Add your IP in subjectAltName in the openssl.cnf before generating # certs
sudo vi /etc/ssl/openssl.cnf
# Add this line
#subjectAltName=IP:192.168.0.2
mkdir -p /certs
openssl req \ -newkey rsa:4096 -nodes -sha256 -keyout certs/domain.key \ -x509 -days 365 -out certs/domain.crt
# Press enter to everything except CN add your ip address thereGenerating a 4096 bit RSA private key
...............................................................................................................................................................................................................................++
............................................................++
writing new private key to 'certs/domain.key'
-----
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [AU]:
State or Province Name (full name) [Some-State]:
Locality Name (eg, city) []:
Organization Name (eg, company) [Internet Widgits Pty Ltd]:
Organizational Unit Name (eg, section) []:
Common Name (e.g. server FQDN or YOUR name) []:192.168.0.2
Email Address []:
What it did is it created two files and in /certs directory. domains.crt and domains.key
sudo docker run -d -p 5000:5000 --restart=always --name registry \ -v /certs:/certs \ -e REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt \ -e REGISTRY_HTTP_TLS_KEY=/certs/domain.key \ registry:2
What this does is it. First downloads the registry:2
image. Second it mounts the /certs
directory that we just created in host machine to a /certs
directory on the docker machine. Also this command adds 2 environment variables REGISTRY_HTTP_TLS_CERTIFICATE and REGISTRY_HTTP_TLS_KEY
to the docker machine to use the newly created certificates. Finally it binds the application running on 5000
in docker machine and exposes it to 5000
in host machine. --restart=always
means that this docker machine too will restart if the docker daemon restarts
To check if it is running properly:
sudo docker ps# Should display
CONTAINER ID IMAGE COMMAND ... 4b6bcbadf307 registry:2 entrypoint...
# now get the container id
sudo docker logs <container-id>
# if you didn't see any obvious error messages then you are good to go
Get a sample image, tag then push to the registry.
# get busybox image from public dockerhub
sudo docker pull busybox
# check the busybox image id
sudo docker images
# tag the image for pushing
sudo docker tag <image-id> 192.168.0.2:5000/busybox
# test pushing the image
sudo docker push 192.168.0.2:5000/busybox
#! ERRORThe push refers to a repository [192.168.0.2:5000/busybox]Get https://192.168.0.2:5000/v1/_ping: x509: certificate signed by unknown authority
Since our certificate is self signed the connection encryption is not trusted by docker.
Go back to /certs/domain.crt
and copy it to docker’s trusted certificate
mkdir -p /etc/docker/certs.d/192.168.0.2:5000cd /certscp /certs/domain /etc/docker/certs.d/192.168.0.2:5000/cd /etc/docker/certs.d/192.168.0.2:5000/mv domains.crt ca.crt
#reload docker daemon to use the certificatesudo service docker reload
Essentially this forces docker to verify our self signed certificate even though it is not signed by a known authority.
However if you saw error message about IP Sans. unable to ping registry endpoint…x509: cannot validate certificate for … because it doesn’t contain any IP SANs . It means you skipped adding subjectAltName on openssl.cnf on Step two. So you have to follow back step 2 again
If it worked you should be able to see message similar to below
4ac76077f2c7: Pushed
latest: digest: sha256:c79345819a6882c31b41bc771d9a94fc52872fa651b36771fbe0c8461d7ee558 size: 527
Congrats! You now have a private docker repository :)
Please feel free to leave comments and feedback below