搭建私人docker镜像库

安装 Docker Engine

这里只演示了Debian系统安装Docker Engine的方法,其他系统参考:[Docker官网文档]

在安装 Docker Engine 之前,需要卸载所有有冲突的非官方软件包。

要卸载的非官方软件包包括:

  • docker.io
  • docker-compose
  • docker-doc
  • podman-docker

运行以下命令来卸载所有冲突的包:

1
for pkg in docker.io docker-doc docker-compose podman-docker containerd runc; do sudo apt-get remove $pkg; done

使用 apt 存储库安装

在新的主机上首次安装 Docker Engine 之前,需要设置 Docker apt存储库。之后,可以从存储库安装和更新 Docker。

设置 Docker 的 apt 存储库

1
2
3
4
5
6
7
8
9
10
11
12
13
# Add Docker's official GPG key:
sudo apt-get update
sudo apt-get install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/debian/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc

# Add the repository to Apt sources:
echo \
"deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/debian \
$(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt-get update

安装 最新的 Docker 包

1
sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

通过运行镜像来验证安装是否成功 hello-world

1
sudo docker run hello-world

或者运行 docker -v:

1
2
root:~# docker -v
Docker version 27.3.1, build ce12230

使用 htpasswd 工具管理访问权限

Debian/Ubuntu 系统中,安装 Apache 工具包:

1
2
sudo apt update
sudo apt install apache2-utils

创建账户:

1
htpasswd -Bc /path/to/auth/htpasswd [username]

这里的 -B 表示使用 bcrypt 加密,-c 表示创建文件。

创建 Docker Registry 容器

方法1:直接使用 docker 命令

1
2
3
4
5
6
7
8
9
docker run -d \
--name registry \
-v /path/to/registry/data:/var/lib/registry \
-v /path/to/auth:/auth \
-e "REGISTRY_AUTH=htpasswd" \
-e "REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm" \
-e "REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd" \
-p 5000:5000 \
registry:2

方法2:使用 Docker Compose(推荐)

新建一个compose.yml文件,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
version: '3.8'
services:
registry:
image: registry:2
ports:
- "5000:5000"
environment:
- REGISTRY_AUTH=htpasswd
- REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm
- REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd
volumes:
- /path/to/registry/data:/var/lib/registry
- /path/to/auth:/auth
  • /path/to/registry/data:docker registry的数据储存目录
  • /path/to/auth:使用htpasswd生成的用户名和密码目录

使用 docker compose up -d 或者 docker-compose up -d 启动

最新版的docker Engine已经自动集成compose了,如果执行报错compose不存在,那么需要手动安装docker compose或者直接采用第一种方案创建容器。

最后检查启动端口是否已经被监听使用:

1
2
3
root:~# lsof -i :5000
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
docker-pr 231380 root 4u IPv4 3129751 0t0 TCP *:5000 (LISTEN)

客户端 Docker 配置

由于我们还没有配置https证书,暂时只能使用http,所以我们需要编辑客户端的Docker配置文件以允许指定服务器ip的http连接:

  • 在 Linux/macOS 上,路径默认是 /etc/docker/daemon.json
  • 在 Windows 上,路径默认是 C:\ProgramData\docker\config\daemon.json

修改客户端docker daemon配置添加或更新以下内容(之后重启docker服务):

1
2
3
{
"insecure-registries": ["x.x.x.x:5000"]
}

登陆目标服务器:

1
2
3
4
➜  ~ docker login x.x.x.x:5000
Username: XXX
Password:
Login Succeeded

标记镜像(这里hello-world表示客户端已有的本地镜像,也可以替换成本地其他镜像)

1
docker tag hello-world x.x.x.x:5000/hello-world

推送镜像:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
➜  ~ docker push x.x.x.x5000/hello-world
Using default tag: latest
The push refers to repository [x.x.x.x:5000/hello-world]
51635e63ab0c: Pushed
1f62b39dc401: Pushed
805908969407: Pushed
6c29a458e7d5: Pushed
b9a670e7a7f3: Pushed
83d624c4be2d: Pushed
2c1384c86539: Pushed
latest: digest: sha256:3c8ba625caaaae90eced8640bd64f6bf87ad68773831837b27b35056df873aef size: 2297

i Info → Not all multiplatform-content is present and only the available single-platform image was pushed
sha256:28402db69fec7c17e179ea87882667f1e054391138f77ffaf0c3eb388efc3ffb -> sha256:3c8ba625caaaae90eced8640bd64f6bf87ad68773831837b27b35056df873aef

拉取镜像:

1
2
3
4
5
6
7
8
9
➜  ~ docker pull x.x.x.x:5000/hello-world
Using default tag: latest
latest: Pulling from hello-world
Digest: sha256:3c8ba625caaaae90eced8640bd64f6bf87ad68773831837b27b35056df873aef
Status: Downloaded newer image for x.x.x.x:5000/hello-world:latest
x.x.x.x:5000/hello-world:latest

What's next:
View a summary of image vulnerabilities and recommendations → docker scout quickview x.x.x.x:5000/hello-world

如果没出现报错的话,已经可以顺利使用了。

配置 HTTPS 证书

配置HTTPS的前提是已经拥有域名和域名证书

更新服务端 docker compose 内容

更新后内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
version: '3'

services:
registry:
image: registry:2
ports:
- "443:443"
environment:
REGISTRY_HTTP_ADDR: "0.0.0.0:443"
REGISTRY_HTTP_TLS_CERTIFICATE: "/certs/fullchain.pem"
REGISTRY_HTTP_TLS_KEY: "/certs/privkey.pem"
REGISTRY_AUTH: htpasswd
REGISTRY_AUTH_HTPASSWD_REALM: "My Private Registry"
REGISTRY_AUTH_HTPASSWD_PATH: "/auth/htpasswd"
volumes:
- /etc/letsencrypt/archive/domian.com:/certs
- /path/to/registry/data:/var/lib/registry
- /path/to/auth/htpasswd:/auth/htpasswd
  • HTTPS更推荐使用443端口而不是5000端口,所以我们改为”443:443”,如果443端口已经被占用,也可以使用”8443:443”或者任何你喜欢的端口
  • /etc/letsencrypt/archive/domian.com 为域名证书目录
  • fullchain.pem 为证书公钥文件名
  • privkey.pem 为证书私钥文件名

使用 docker compose up -d 或者 docker-compose up -d 启动

测试 HTTPS 连接

后续操作假设你的域名registry.domain.com已经指向 [your_ip]:[port],当然也可以是其它子域名。如果没有,请使用registry.domain.com:[port]代替registry.domain.com测试连接

  • 客户端登陆

    1
    docker login registry.domain.com
  • 标记镜像

    1
    docker tag registry.domain.com/hello-world
  • 推送镜像

    1
    docker push registry.domain.com/hello-world
  • 拉取镜像

    1
    docker pull registry.domain.com/hello-world

至此,如果都没有问题,那么恭喜私人的docker镜像仓库搭建就成功了。