前面系列文章已经讲了《Docker及Docker仓库》和《Docker for Mac和Kubernetes的安装配置》的一些知识,本章主要介绍Docker Registry搭建过程。不需要认证的Docker Registry搭建过程很简单,官方文档讲的很清楚。
Docker Registry的自签发证书、公网访问、登录认证相对比较复杂。
一、 Insecure Registry
下载registry镜像后直接运行:
docker run -d -p 5000:5000 --restart=always --name registry -v /Users/zhuxihua/registry:/var/lib/registry registry:2
不过,在docker push的时候遇到如下错误:
1.1 一般解决方法
在/etc/docker/daemon.json
1.2 解决方法
修改Registry server上的Docker daemon的配置,为DOCKER_OPTS增加–insecure-registry:DOCKER_OPTS="--insecure-registry xxx:5000”。
重启Docker Daemon,启动Registry容器:
$ sudo service docker restart
docker stop/waiting
docker start/running, process 6712
$ sudo docker run -d -p 5000:5000 --restart=always --name registry -v /Users/zhuxihua/registry:/var/lib/registry registry:2
尝试再次Push image:
$ docker push xxxx:5000/test/busybox
The push refers to a repository
[xxxx:5000/test/busybox] (len: 1) 65e4158d9625: Pushed
5506dda26018: Pushed
latest: digest: sha256:800f2d4558acd67f52262fbe170c9fc2e67efaa6f230a74b41b555e6fcca2892 size: 2739
push ok!
二、Secure Registry
Docker官方是推荐你采用Secure Registry的工作模式的,即transport采用tls。这样我们就需要为Registry配置tls所需的key和crt文件了。
我们首先清理一下环境,将上面的Insecure Registry停掉并rm掉;将各台主机上Docker Daemon的DOCKER_OPTS配置中的–insecure-registry去掉,并重启Docker Daemon。
如果你拥有一个域名,域名下主机提供Registry服务,并且你拥有某知名CA签署的证书文件,那么你可以建立起一个Secure Registry。不过我这里没有现成的证书,只能使用自签署的证书。严格来讲,使用自签署的证书在Docker官方眼中依旧属于Insecure,不过这里只是借助自签署的证书来说明一下Secure Registry的部署步骤罢了。
2.1 制作自签署证书
如果你有知名CA签署的证书,那么这步可直接忽略。
$ openssl req -newkey rsa:2048 -nodes -sha256 -keyout certs/domain.key -x509 -days 365 -out certs/domain.crt
Generating a 2048 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]:CN
State or Province Name (full name) [Some-State]:SC
Locality Name (eg, city) []:CD
Organization Name (eg, company) [Internet Widgits Pty Ltd]:WW
Organizational Unit Name (eg, section) []:YF
Common Name (e.g. server FQDN or YOUR name) []:mydockerhub.com
Email Address []:503172601@qq.com
2、启动Secure Registry
启动带证书的Registry:
docker run -d -p 5000:5000 --restart=always --name registry \
-v `pwd`/auth:/auth \
-e "REGISTRY_AUTH=htpasswd" \
-e "REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm" \
-e REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd \
-v `pwd`/certs:/certs \
-v /Users/zhuxihua/registry:/var/lib/registry \
-e REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt \
-e REGISTRY_HTTP_TLS_KEY=/certs/domain.key \
registry:2
由于证书的CN是mydockerhub.com,我们需要修改一下/etc/hosts文件:
xxxx.xxxx.xxxx.xxxx mydockerhub.com
重新为busybox制作一个tag:
$docker tag busybox:latest mydockerhub.com:5000/test/busybox:latest
Push到Registry:
$ docker push mydockerhub.com:5000/test/busybox
The push refers to a repository [mydockerhub.com:5000/test/busybox] (len: 1)
unable to ping registry endpoint https://mydockerhub.com:5000/v0/
v2 ping attempt failed with error: Get https://mydockerhub.com:5000/v2/: x509: certificate signed by unknown authority
v1 ping attempt failed with error: Get https://mydockerhub.com:5000/v1/_ping: x509: certificate signed by unknown authority
push失败了!从错误日志来看,docker client认为server传输过来的证书的签署方是一个unknown authority(未知的CA),因此验证失败。我们需要让docker client安装我们的CA证书:
$ sudo mkdir -p /etc/docker/certs.d/mydockerhub.com:5000
$ sudo cp certs/domain.crt /etc/docker/certs.d/mydockerhub.com:5000/ca.crt
$ sudo service docker restart //安装证书后,重启Docker Daemon
另外,macOS的用户还需要额外执行下面的命令:
sudo security add-trusted-cert -d -r trustRoot -k /Library/Keychains/System.keychain ca.crt
再执行Push,我们看到了成功的输出日志。
3、外部访问Registry
我们换其他机器试试访问这个secure registry。根据之前的要求,我们照猫画虎的修改一下hosts文件,安装ca.cert,去除–insecure-registry选项,并重启Docker daemon。
如果使用自签署的证书,那么所有要与Registry交互的Docker主机都需要安装mydockerhub.com的ca.crt(domain.crt)。
三、Registry的鉴权管理
Registry提供了一种基础的鉴权方式。我们通过下面步骤即可为Registry加上基础鉴权:在Register server上,为Registry增加bigdatafly用户,密码123456。
- 生成鉴权密码文件
$ mkdir auth
$ docker run --entrypoint htpasswd registry:2 -Bbn foo foo123 > auth/htpasswd
$ ls auth
htpasswd
- 启动带鉴权功能的Registry:
docker run -d -p 5000:5000 --restart=always --name registry \
-v `pwd`/auth:/auth \
-e "REGISTRY_AUTH=htpasswd" \
-e "REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm" \
-e REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd \
-v `pwd`/certs:/certs \
-v /Users/zhuxihua/registry:/var/lib/registry \
-e REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt \
-e REGISTRY_HTTP_TLS_KEY=/certs/domain.key \
registry:2
执行docker login:
$docker login mydockerhub.com:5000
Username: bigdatafly
Password:
Email: bigwhite.cn@gmail.com
WARNING: login credentials saved in /home/baiming/.docker/config.json
Login Succeeded
四、Registry中images的管理
前面提到过,通过V2版Rest API可以查询Repository和images:
$ curl --cacert domain.crt --basic --user foo:foo123 https://mydockerhub.com:5000/v2/_catalog
{"repositories":["test/busybox","test/ubuntu"]}
但如果要删除Registry中的Repository或某个tag的Image,目前v2还不支持,原因见Registry的roadmap中的说明。不过如果你的Registry的存储引擎使用的是本地盘,倒是有一些第三方脚本可供使用,比如:delete-docker-registry-image。
五、小结
Docker Registry终于安装成功,下一步终于可以创建Eureka-Server工程了。