Docker 安装与Registry V2私有仓库搭建

Docker 是一个开源的容器引擎,可以让开发者把应用以及依赖打包到一个可移植的容器中。Docker 采用Go语言编写,当时学习Go语言的时候已经知道这个神器,但是一直没有合适的场景正式使用,现在机会来啦。

Registry 是Docker 镜像的仓库,使用Registry 能搭建私有的Docker仓库,方便分发自定义镜像。

环境

本文的内容在以下版本中测试通过,不同的版本可能存在不同的地方,以下内容仅供参考。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
[root@CentOS72-40 /]# cat /etc/centos-release
CentOS Linux release 7.2.1511 (Core)

[root@CentOS72-40 /]# docker version
Client:
Version: 1.12.3
API version: 1.24
Go version: go1.6.3
Git commit: 6b644ec
Built:
OS/Arch: linux/amd64

Server:
Version: 1.12.3
API version: 1.24
Go version: go1.6.3
Git commit: 6b644ec
Built:
OS/Arch: linux/amd64

[root@CentOS72-40 /]# docker images registry
REPOSITORY TAG IMAGE ID CREATED SIZE
registry 2.5.1 c9bd19d022f6 4 weeks ago 33.27 MB

Docker 安装

安装Docker 需要内核是3.10 以上64位的Linux 系统。查看Linux 内核版本,CentOS7.2是没问题的。(现在Mac 和 Windows 都可以安装Docker)

1
2
[root@CentOS72-40 ~]# uname -r
3.10.0-327.36.3.el7.x86_64

CentOS 7 之后的默认防火墙是firewall,习惯使用iptables 做防火墙,所以还是修改为iptables 做防火墙。
停止firewall ,然后禁止firewall 开机启动。

1
2
[root@CentOS72-40 ~]# systemctl stop firewalld
[root@CentOS72-40 ~]# systemctl disable firewalld

检查iptables 的状态,若没有安装iptables 服务则需要安装iptables-services。

1
2
3
4
5
6
[root@CentOS72-40 ~]# systemctl status iptables
· iptables.service
Loaded: not-found (Reason: No such file or directory)
Active: inactive (dead)

[root@CentOS72-40 ~]# yum install iptables-services

编辑iptables 防火墙文件,开放22和5000端口(5000端口供Registry对外提供服务)。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
[root@CentOS72-40 ~]# vim /etc/sysconfig/iptables

# sample configuration for iptables service
# you can edit this manually or use system-config-firewall
# please do not ask us to add additional ports/services to this default configuration
*filter
:INPUT ACCEPT [0:0]
:FORWARD ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
-A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
-A INPUT -p icmp -j ACCEPT
-A INPUT -i lo -j ACCEPT
-A INPUT -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT
-A INPUT -p tcp -m state --state NEW -m tcp --dport 5000 -j ACCEPT

-A INPUT -j REJECT --reject-with icmp-host-prohibited
-A FORWARD -j REJECT --reject-with icmp-host-prohibited
COMMIT

设置iptables 防火墙开机启动,启动防火墙使更改的配置生效。

1
2
[root@CentOS72-40 ~]# systemctl enable iptables
[root@CentOS72-40 ~]# systemctl start iptables

创建Docker 的yum 的仓库。

1
2
3
4
5
6
7
8
[root@CentOS72-40 ~]# tee /etc/yum.repos.d/docker.repo <<-'EOF'
[dockerrepo]
name=Docker Repository
baseurl=https://yum.dockerproject.org/repo/main/centos/7/
enabled=1
gpgcheck=1
gpgkey=https://yum.dockerproject.org/gpg
EOF

安装docker-engine 会自动安装依赖 docker-engine-selinux。

1
[root@CentOS72-40 ~]# yum install docker-engine

设置开机启动docker,然后启动docker。

1
2
[root@CentOS72-40 ~]# systemctl enable docker
[root@CentOS72-40 ~]# systemctl start docker

安装完docker之后将会发现创建docker0网卡。

1
2
3
4
5
6
7
8
[root@CentOS72-40 /]# ifconfig
docker0: flags=4099<UP,BROADCAST,MULTICAST> mtu 1500
inet 172.17.0.1 netmask 255.255.0.0 broadcast 0.0.0.0
ether 02:42:2b:79:c2:73 txqueuelen 0 (Ethernet)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

配置Registry

拉取2.5.1版本的Registry 镜像。

1
[root@CentOS72-40 /]# docker pull registry:2.5.1

启动Registry镜像。根据Registry的文档把/tmp/registry-dev 目录映射出来是有问题的,真正的数据不是存储再这个目录。不知道是不新版的存在这个目录,反正2.5.1版的Registry 数据不是保存在这里,进入容器发现真正存储镜像的时在/var/lib/registry 目录,所以把这个目录映射出来。(跟着官方文档居然也走不通,郁闷,会不会是官方故意挖个坑让大家踩的呢)

1
[root@CentOS72-40 /]# docker run -d -p 5000:5000 -v /data/registry:/var/lib/registry --name registry registry:2.5.1

打开http://172.18.2.40:5000/v2/_catalog 验证是否安装成功。

若是启用iptables的时候没有放开5000端口,在registry 运行的时候再放开。之后停了registry 重新打开registry 就会有下面的错误。不仅仅是Registry这个容器存在这个问题,所有容器的在运行中,主机的iptables 被修改过,停了容器再启动都会有这个问题。目前没有找到好的解决版本,但是重新启动docker 服务 systemclt restart docker 可以临时解决这个问题。

1
2
Error response from daemon: driver failed programming external connectivity on endpoint registry (4b748e54bb59d8bfe1f1bd961c6f0fcfbd8ec94c75c5d4880134bd2a453b0d51): iptables failed: iptables --wait -t nat -A DOCKER -p tcp -d 0/0 --dport 5000 -j DNAT --to-destination 172.17.0.2:5000 ! -i docker0: iptables: No chain/target/match by that name.
(exit status 1)

使用Registry

对已经存在的镜像wendyeq/tomcat8 打上带Registry地址的tag,版本号位1.0。然后推送到Registry,发现推送不了,原因是Registry V2采用https协议。

1
2
3
4
[root@M-CentOS72-36 ~]# docker tag wendyeq/tomcat8 172.18.2.40:5000/wendyeq/tomcat8:1.0
[root@M-CentOS72-36 ~]# docker push 172.18.2.40:5000/wendyeq/tomcat8:1.0
The push refers to a repository [172.18.2.40:5000/wendyeq/tomcat8]
Get https://172.18.2.40:5000/v1/_ping: http: server gave HTTP response to HTTPS client

解决这个问题的最简单方式是修改docker的启动脚本,添加-H tcp://127.0.0.1:2375 -H unix:///var/run/docker.sock --insecure-registry 172.18.2.40:5000 内容。

1
2
3
4
5
6
7
8
[root@M-CentOS72-36 ~]# vim /usr/lib/systemd/system/docker.service

[Service]
Type=notify
# the default is not to use systemd for cgroups because the delegate issues still
# exists and systemd currently does not support the cgroup feature set required
# for containers run by docker
ExecStart=/usr/bin/dockerd -H tcp://127.0.0.1:2375 -H unix:///var/run/docker.sock --insecure-registry 172.18.2.40:5000

修改完之后就可以推送到Registry 的私有仓库啦。

1
2
3
4
5
6
[root@M-CentOS72-36 ~]# systemctl start docker
Warning: docker.service changed on disk. Run 'systemctl daemon-reload' to reload units.
[root@M-CentOS72-36 ~]# systemctl daemon-reload
[root@M-CentOS72-36 ~]# systemctl start docker
[root@M-CentOS72-36 ~]# docker push 172.18.2.40:5000/wendyeq/tomcat8
The push refers to a repository [172.18.2.40:5000/wendyeq/tomcat8]

总结

Docker 和 Registry 的安装都比较简单,但是Registry查找镜像好麻烦,特别是查看版本号,要好好研究一下Registry 的文档才行。