Insecure And Self-Signed Private Docker Registry With Boot2Docker
Let's take a look at how to set up an insecure docker registry and a self-signed docker registry on Digital Ocean. Then we will attempt to access the registry via basic authentication with boot2docker.
What I use:
- Docker 1.9.0
- Docker Machine 0.5.0 (version 1.9.0, build master : 16e4a2a)
- Docker Registry 2
- Digital Ocean account
Create A Registry Host
To create the registry host on Digital Ocean:
$docker-machine create --driver digitalocean \
--digitalocean-access-token <our_digitalocean_token> \
--digitalocean-region <our_region> \
registry
This creates a droplet named registry
in <our_region>
, defaulted to 512MB of memory and 20GB of hard disk storage, with an auto-assign public floating IP address.
Set Up Docker Registry 2.0
Let's SSH into our droplet and set up a docker registry.
$eval `docker-machine env registry`
$docker-machine ssh registry
root@registry-02:~# docker run -d -p 5000:5000 \
--restart=always --name registry \
-v `pwd`/data:/var/lib/registry \
registry:2
This should get Docker Registry 2.0 running on our host. We can verify this by using docker ps
.
If we tried to push a docker image to our registry now, it should fail. (In my case, I am using boot2docker.)
$docker pull isim/consul # pull from docker hub
$docker tag isim/consul <floating_ip>:5000/consul # tag for remote repository
$docker push <floating_ip>:5000/consul # push to my registry
The push refers to a repository [198.199.110.18:5000/consul] (len: 1)
unable to ping registry endpoint https://198.199.110.18:5000/v0/
v2 ping attempt failed with error: Get https://198.199.110.18:5000/v2/: tls: oversized record received with length 20527
v1 ping attempt failed with error: Get https://198.199.110.18:5000/v1/_ping: tls: oversized record received with length 20527
Trust An Insecure Registry
To tell our local Docker to disregard security and trust our docker registry as an insecure registry, make the following changes in our local Docker (not our registry host). In my case, this changes need to be done to my boot2docker.
$docker-machine ssh default #ssh into boot2docker
docker@default:~$ sudo vi /var/lib/boot2docker/profile #update boot2docker profile to trust the insecure registry
Add the floating IP of your registry node to EXTRA_ARGS
as an insecure registry in the boot2docker profile file:
EXTRA_ARGS='
--label provider=virtualbox
--insecure-registry=198.199.110.18:5000
'
Exit out of boot2docker and restart it using docker-machine. Now attempt to push our newly tagged image again, and it should work.
Since we run our registry with a mounted volume earlier, we should see the image stored under the volume source. In my case, my registry host looks like:
root@registry:~# ls -al data/docker/registry/v2/repositories/
total 12
drwxr-xr-x 3 root root 4096 Nov 29 19:37 .
drwxr-xr-x 4 root root 4096 Nov 29 19:37 ..
drwxr-xr-x 5 root root 4096 Nov 29 19:38 consul
Please read up on the pros-and-cons of insecure registry.
Self-Signed Registry With Access Restriction
Remove the --insecure-registry
flag from our boot2docker profile file and restart our boot2docker. We will now create our own self-signed certificate, secure our registry with TLS, and then restrict access to it using Basic Auth.
To generate a self-signed certificate on our registry host:
root@registry:~# mkdir certs
root@registry:~# openssl req \
-newkey rsa:4096 -nodes -sha256 \
-keyout certs/domain.key \
-x509 -days 356 \
-out certs/domain.crt
When prompted for Common Name (e.g. server FQDN or YOUR name)
, I use <floating_ip>.xip.io
. You can read more about xip.io here. We should see our private keys and certificates in the certs/
folder.
To set up basic auth on our registry host:
root@registry:~# mkdir auth
root@registry:~# docker run --entrypoint htpasswd registry:2 -Bnb <username> <password> > auth/htpasswd
This will create a auth/htpasswd
file.
Stop and remove our running docker registry. (/data
folder should still be intact.) Restart it to pick up the certs and password:
docker run -d -p 5000:5000 --restart=always --name registry \
-v `pwd`/auth:/auth \
-v `pwd`/certs:/certs \
-v `pwd`/data:/var/lib/registry \
-e "REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt" \
-e "REGISTRY_HTTP_TLS_KEY=/certs/domain.key" \
-e "REGISTRY_AUTH=htpasswd" \
-e "REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm" \
-e "REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd"
registry:2
Now we have to update the Docker daemon on our boot2docker to trust the certificates.
docker@default:~$ sudo mkdir -p /etc/docker/certs.d/<floating_ip>.xip.io:5000
docker@default:~$ sudo vi /etc/docker/certs.d/<floating_ip>.xip.io:5000/ca.crt # copy certificate from registry host to this file
Create the /etc/docker/certs.d/<floating_ip>.xip.io:5000
folder and copy our certs/domain.crt
certificate from our registry host to /etc/docker/certs.d/<floating_ip>.xip.io:5000/ca.crt
.
Restart our docker daemon.
docker@default:~$ sudo /etc/init.d/docker restart
Now we should be able to push image and login to our registry host.
$docker login <floating_ip>.xip.io:5000
WARNING: login credentials saved in ~/.docker/config.json
Login Succeeded
$docker tag isim/consul <floating_ip>.xip.io:5000/consul
$docker push <floating_ip>.xip.io:5000/consul
Notice the usage of the xip.io
domain.
Written by Ivan Sim
Related protips
4 Responses
Great read, it works if using insecure-registry.
But failed using Self-Signed cert, error msg: if you have access to the registry's CA certificate, no need for the flag; simply place the CA certificate at /etc/docker/certs.d/host:port/ca.crt
However it succeeded if using curl to access using the cert.
sudo curl --cacert /etc/docker/certs.d/host:port/ca.crt https://user:pass@host:port/v2
Any ideas please? thanks
BTW: I'm using docker version 1.9.1, never succeeded neither on mac nor on linux.
@gembinz I haven't seen that error before. May have to google the error to see what's going wrong. If you are able to curl the endpoint, does that mean the registry container is up and running?
Adding the insecure registry flag was something that I was stuck with for a long time. Thanks for this post and it saved my day!! :)