自建Docker Registry Mirror:安全高效的容器镜像解决方案_docker registry-mirrors
文章目录
- 1 背景
- 2 解决方案
- 3 小结
- 4 参考资料
1 背景
近年来,随着docker hub被封禁,国内的公共docker registry因为法规问题纷纷关闭, pull个docker镜像变得困难起来。
网络上有一些免费的镜像源可用,但是这些镜像源存在以下几个问题:
- 不稳定。小于200M的文件多试几次也可以下载下来,但大于200M的文件就很难成功下载了。
- 时效性低。这些源可能一段时间之后就失效了。
- 不安全。使用这些【免费】的镜像源,尤其是不知名的三方源,存在一个重大风险:docker镜像投毒。攻击者会搭建一个恶意代理站,通过钓鱼邮件、恶意广告或供应链攻击,诱导目标用户或企业将 Docker 客户端配置指向这个恶意代理站(例如,声称提供“更快”、“更稳定”或“免费”的镜像加速服务,之后攻击者会篡改 Docker 镜像,在其中植入恶意代码、后门、漏洞利用程序或其他有害载荷,它是 Docker 镜像投毒攻击中一种极其高级、危害巨大且极难被常规手段发现的形式。
2 解决方案
解决这个问题的方法之一就是自建 docker registry mirror。
2.1 硬件准备
首先要有一台海外服务器,可以障碍地访问 docker hub: https://hub.docker.com/
2.2 使用docker compose 安装 docker registry
Docker Registry 是一个用于存储和管理 Docker 镜像的服务,它允许用户上传(push)、下载(pull)、管理和共享容器镜像。Docker 官方提供了 registry 镜像,用户可以基于它快速搭建私有镜像仓库。为便于行文,下面都使用registry来指代docker registry。
docker-compose.yaml配置
新建一个docker-compose.yaml文件,写入以下内容:
services: server: image: registry:2.8 restart: always ports: - 5000:5000 volumes: - ./config.yml:/etc/docker/registry/config.yml - ./auth:/auth - ./storage:/var/lib/registry
配置说明:
- 指定使用 registry:2.8, 版本号一定要指定,否则会拉取最新版本,最新版本的registry的配置跟2.8版本的会不一样,这个会导致出现一些莫名其妙的问题。
./config.yml
为 registry 的配置文件。./auth
为身份认证信息的存储位置。./storage
为镜像文件的存放位置。
config.yml 配置
新建一个config.yml文件,写入以下内容:
version: 0.1proxy: remoteurl: https://registry-1.docker.iostorage: filesystem: rootdirectory: /var/lib/registryhttp: addr: 0.0.0.0:5000 headers: X-Content-Type-Options: [nosniff]auth: htpasswd: realm: basic-realm path: /auth/htpasswd
配置说明:
proxy
: 此为关键配置,它配置一个代理(proxy),指向docker hub镜像源<https://registry-1.docker.io.auth
: 配置身份认证方式,以及数据存放位置。
身份认证配置
安装htpasswd工具(以centos 7为例):
yum -y install httpd-tools
验证:
htpasswd -h
创建用户名和密码:
htpasswd -Bbn <用户名> <密码> > auth/htpasswd示例:htpasswd -Bbn admin spHNCh67z2fQy6azwMKp > auth/htpasswd
说明:
- 请将和替换为你的用户名和密码
- 用户名和密码将被保存在 auth/htpasswd文件中。
- 注意上面的 > 符号,不要漏掉了。
https支持
如果是个人使用,仅使用http就够了。
如果想配置https,需要先准备一个域名 + 一个ssl证书,可使用nginx来实现http转https。
启动 registry 服务
docker compose up -d
2.3 docker cli客户端配置
假定海外服务器的ip为:aaa.bbb.ccc.ddd。
编辑 daemon.json文件
vim /etc/docker/daemon.json
将文件内容修改为:
{ \"registry-mirrors\": [ \"http://aaa.bbb.ccc.ddd:5000\" ], \"insecure-registries\": [ \"aaa.bbb.ccc.ddd:5000\" ]}
说明:
- aaa.bbb.ccc.ddd 为你的海外服务器的公网ip。
- registry-mirrors 用于配置一个registry mirror,这个在pull包时有效。
- insecure-registries用于配置一个使用http访问的registry,这个在push包到这个registry时有效。
重启docker服务:
sudo systemctl daemon-reloadsudo systemctl restart docker
登录 registry mirror
docker login aaa.bbb.ccc.ddd:5000
按照提示输入上面设置的用户名和密码。如下:
拉取镜像
假定要拉取node 21,执行以下命令:
docker pull aaa.bbb.ccc.ddd:5000/library/node:22
注意事项:
- 拉取时要加上ip前缀,
- 如果是官方库,要加上library前缀,比如node、nginx等都是官方库。官方库是原先通过docker pull xxx 就可以拉取的镜像,官方为了便于官方库的使用,省略了library前缀。
3 小结
自建Docker Registry Mirror方案有效解决了以下问题:
- 突破了国内访问Docker Hub的限制
- 避免了使用不可靠第三方源的安全风险
- 提供了稳定的镜像获取渠道
- 配置简单,维护成本低
4 参考资料
docker镜像投毒
Apache htpasswd命令用法详解