Release v1.5.0: Restructure chapters and update for Docker v30.x

This commit is contained in:
Baohua Yang
2026-02-04 22:12:38 -08:00
parent b4b0d4160a
commit fdb879dcf2
304 changed files with 1314 additions and 364 deletions

7
06_repository/README.md Normal file
View File

@@ -0,0 +1,7 @@
# 访问仓库
仓库`Repository`是集中存放镜像的地方
一个容易混淆的概念是注册服务器`Registry`实际上注册服务器是管理仓库的具体服务器每个服务器上可以有多个仓库而每个仓库下面有多个镜像从这方面来说仓库可以被认为是一个具体的项目或目录例如对于仓库地址 `docker.io/ubuntu` 来说`docker.io` 是注册服务器地址`ubuntu` 是仓库名
大部分时候并不需要严格区分这两者的概念

View File

@@ -0,0 +1,2 @@
username:$2y$05$TRWvCC6ilpKpY3ICifw32Ok3.8SpG3etq8O5WGdCm9wvyDhtSbRgy

View File

@@ -0,0 +1,35 @@
version: 0.1
log:
accesslog:
disabled: true
level: debug
formatter: text
fields:
service: registry
environment: staging
storage:
delete:
enabled: true
cache:
blobdescriptor: inmemory
filesystem:
rootdirectory: /var/lib/registry
auth:
htpasswd:
realm: basic-realm
path: /etc/docker/registry/auth/nginx.htpasswd
http:
addr: :5000
host: https://docker.domain.com
headers:
X-Content-Type-Options: [nosniff]
http2:
disabled: false
tls:
certificate: /etc/docker/registry/ssl/docker.domain.com.crt
key: /etc/docker/registry/ssl/docker.domain.com.key
health:
storagedriver:
enabled: true
interval: 10s
threshold: 3

View File

@@ -0,0 +1,13 @@
services:
registry:
image: registry:2
ports:
- "443:5000"
volumes:
- ./:/etc/docker/registry
- registry-data:/var/lib/registry
volumes:
registry-data:

View File

@@ -0,0 +1,4 @@
[root_ca]
basicConstraints = critical,CA:TRUE,pathlen:1
keyUsage = critical, nonRepudiation, cRLSign, keyCertSign
subjectKeyIdentifier=hash

View File

@@ -0,0 +1,7 @@
[server]
authorityKeyIdentifier=keyid,issuer
basicConstraints = critical,CA:FALSE
extendedKeyUsage=serverAuth
keyUsage = critical, digitalSignature, keyEncipherment
subjectAltName = DNS:docker.domain.com, IP:127.0.0.1
subjectKeyIdentifier=hash

View File

@@ -0,0 +1,35 @@
-----BEGIN CERTIFICATE-----
MIIF/zCCA+egAwIBAgIJAMbgVbFo7I6IMA0GCSqGSIb3DQEBCwUAMHoxCzAJBgNV
BAYTAkNOMQ8wDQYDVQQIDAZTaGFueGkxDzANBgNVBAcMBkRhdG9uZzEaMBgGA1UE
CgwRWW91ciBDb21wYW55IE5hbWUxLTArBgNVBAMMJFlvdXIgQ29tcGFueSBOYW1l
IERvY2tlciBSZWdpc3RyeSBDQTAeFw0xNzEyMTExMTI2NTRaFw0xOTEyMzExMTI2
NTRaMGcxCzAJBgNVBAYTAkNOMQ8wDQYDVQQIDAZTaGFueGkxDzANBgNVBAcMBkRh
dG9uZzEaMBgGA1UECgwRWW91ciBDb21wYW55IE5hbWUxGjAYBgNVBAMMEWRvY2tl
ci5kb21haW4uY29tMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA1Hbm
1tZvAeC8J54pQLHTVCtrICQ8KFTLOZakPHSWox8iQ4i2fkZaSccvE/51LIFnCM1y
yZv88ILucqitG4zvuhDG+cU8w1vRbWf3xfGCCsHyn6LKBHR0Kk6+WRIBZTdRSsW8
ZvpL2Y7eBNAUkC2oeaOJEOQ8D50b3u5jhAFmXuAcTiZh90Ve4JBKZV8dGs8L81vO
vb7tqvJrEvCNKuZO7mEcjXkgiwUdP3pkZYa0tPOV5UrLH/oEvgPDJfXrNntCY1+A
+CBQ7Sq3S2YpNJN7VnK6SboRi7xpOEgQOXwNVJWm/5YBvnbAztNXKcE2q2wREL9T
ulUJCqo2h6NRaGYPfiLZIUHEJ7vQitRBRDpkxcX8XJX3Jm7weRPXLDOG8RN3FzPD
TGL2ZDTWKDIQ20OhYEmENInKkpC2bYpwMzNvBA7AJN6MCYHXl4VP/Df0pPtMM/Di
ZX+68ng3RQXT5VzDYURIH2wP5kcTL0irsNr+L7lHD+5mA1VErdQsh6AHWjrwMrSM
egJpLP11rK4J+P/HHnqsBEi5XZI/hvRmwD7gwskRqXdDMHaWnoIIpPO3TeNYQUjD
xaV5KUQuWVME5Ihuy03FPMChXXB0WF+tclPJxjQyDkwEVL+6d8i5yCPUBS2gBSBy
pQQINFH4hOcx2e9Lujx7dOWfidjX3xssC9bEe60CAwEAAaOBmjCBlzAfBgNVHSME
GDAWgBTS1B3CPFKA/HcI0cdE8YD4zG143DAMBgNVHRMBAf8EAjAAMBMGA1UdJQQM
MAoGCCsGAQUFBwMBMA4GA1UdDwEB/wQEAwIFoDAiBgNVHREEGzAZghFkb2NrZXIu
ZG9tYWluLmNvbYcEfwAAATAdBgNVHQ4EFgQUSanj6Cs4KVEKaK6/+VA/fNwNg4Ew
DQYJKoZIhvcNAQELBQADggIBAKYtI1WKAL4FoSgH6sTZakw6h90uebrxm9ojeZTA
k0ues8bGTu3w3dsphd9J0V27oz/dGjkwoIzy4QMYC4h6epKVadWfDhnHUPUT1JIC
nGl7qFR539CSPzW+J1mVAGTZ1QONVxe6rFEDRXTsm9oUNq9LUB6a9EBO/9O0x2o7
SZVUJd2WfMGAhqYjKCtMt+8kQgPxayok5IwWLBf03nluoF09Xu1WbY3f9wGNrzQp
ulNlLzkU3f7+dVgF4lvIbr4MPWSQL2A0RYYjqWuwvUlXggtR+Nl6ldotDe7Ae18V
KhQPJzM4muHjRY5dLkzQIIAQifxNprZCYiurUCAmOyOcHYMt5RuiVUPlB/2hoP/E
tuFqq66v0qsE4mCfmJrRq+Yjfgcqsg1quRpjWh9DWOGa9HUeYFkLEKOgXybxVHJQ
ktYba34ZFfBJUMcbZRYrRH6R4zu4LpRiyiXm29F5ml9tarThDZB5g5DJ6BTEt3Zw
+qQHsIAcmHZvJPKEZmM6883gxbGQQ1Xt7iDrp94YRXMguBMbJwEsqI7w+25BHija
Hp4gctdoBvkQBYpXoEsn8wnguofqJt/JhVgu0EQXR4j3U0uI+Oo9ODHFb5t2T26w
EifwcLH+NyUNmUQH45lxaCzb+tqFlP7cbHsdPniaS4AtmBYwKNJMjcrgxnZPtfy1
7zJA
-----END CERTIFICATE-----

View File

@@ -0,0 +1,51 @@
-----BEGIN RSA PRIVATE KEY-----
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
oKnsMQKCAQEA0iurbnOyrF050SfRdQcnG4shZs/HeBT2EB3CsR1OocWwXBeUkBlO
OKl+d1cYan1ppw+qGlbdQr+t3u7lLPFLUBghf+I/8CmSyiCbZlR4/LrePOmw551r
YXU1uvtFu/mQq3ieV+k4GOyHq3lhCDd61QFedyESfbkVK8f4ihvvX3izZAAtZfwU
HcmZ174vpwZploWQPsrL9A2B+Na42ccLM2qA45nPwXv1Jr/U6b/CzPw7r/4DvTXv
FIeolrELDkCgWBQ8lxB7Lt96BZy9Rbiwi1TzcP++BQu4IOwbAfq23tCybu8vDde4
Z15KVf7qyBansdqKx0njxWNu2/dpgKCPqQKCAQEAzWV4aajox7eeTi3iudP1Oxu3
OBiu8xie4xq0mlM13tMxAQry/uOAuTxbaQ48mNsSXdeYeSgmT45lUvFWROqdVScK
8gh04G1NiRAkITzXwCCwKkAQxvQppgypZ+aksBHkFQFBAIg2/mLizS4cicXNEY4G
vb+RImfn8MSqSMLu3cJ8zgFyqfRg6F0oHg9EgEwvbnCLYglN6Xm5KlZutjW4eu7m
Q+1y0lg05e7vFyj2UIVylfzT/aoF/xzXzNt9/LZs0klO3vMmaVyTjuF/71+AyphH
FTmpNs1wpZU2IRqKOMrimIhk6TTxvMSaN4pxKdLPqgHYLWhwkbsdmqtTnCljRg==
-----END RSA PRIVATE KEY-----

126
06_repository/dockerhub.md Normal file
View File

@@ -0,0 +1,126 @@
# Docker Hub
## 什么是 Docker Hub
[Docker Hub](https://hub.docker.com/) 是 Docker 官方维护的公共镜像仓库,也是全球最大的容器镜像库。
它提供了
- **官方镜像** Docker 官方和软件厂商 Nginx, MySQL, Node.js维护的高质量镜像
- **个人/组织仓库**用户可以上传自己的镜像
- **自动构建** GitHub/Bitbucket 集成需付费
- **Webhooks**镜像更新时触发回调
---
## 核心功能
### 1. 搜索镜像
除了网页搜索也可以使用命令行
```bash
$ docker search centos
NAME DESCRIPTION STARS OFFICIAL
centos The official build of CentOS. 7000+ [OK]
```
> **技巧**始终优先使用 `OFFICIAL` 标记为 `[OK]` 的镜像安全性更有保障
### 2. 拉取镜像
```bash
$ docker pull nginx:alpine
```
### 3. 推送镜像
需要先登录
```bash
$ docker login
# 输入用户名和密码
```
打标签并推送
```bash
# 1. 标记镜像
$ docker tag myapp:v1 username/myapp:v1
# 2. 推送
$ docker push username/myapp:v1
```
---
## 限制与配额重要
### 镜像拉取限制 (Rate Limiting)
2020 11 月起Docker Hub 对匿名和免费用户实施了拉取速率限制
| 用户类型 | 限制 |
|---------|------|
| **匿名用户** (未登录) | 6 小时 100 次请求 |
| **免费账户** (已登录) | 6 小时 200 次请求 |
| **Pro/Team 账户** | 无限制 |
> **提示**如果在 CI/CD 环境中遇到 `toomanyrequests` 错误建议
> 1. CI 中配置 `docker login`
> 2. 使用国内镜像加速器
> 3. 搭建私有仓库代理
---
## 安全最佳实践
### 1. 启用 2FA (双因素认证)
Account Settings -> Security 中启用 2FA保护账号安全启用后CLI 登录需要使用 **Access Token** 而非密码
### 2. 使用 Access Token
不要在脚本或 CI/CD 中直接使用登录密码
1. Docker Hub -> Account Settings -> Security -> Access Tokens 创建 Token
2. 使用 Token 作为密码登录
```bash
$ docker login -u username -p dckr_pat_xxxxxxx
```
### 3. 关注镜像漏洞
Docker Hub 会对官方镜像和付费用户的镜像进行安全扫描在镜像标签页可以看到漏洞扫描结果
---
## Webhooks
当镜像被推送时可以自动触发 HTTP 回调例如通知 CI 系统部署
**配置方法**
仓库页面 -> Webhooks -> Create Webhook
---
## 自动构建 (Automated Builds)
> 目前仅限付费用户 (Pro/Team) 使用
链接 GitHub/Bitbucket 仓库后当代码有提交或打标签时Docker Hub 会自动运行构建这保证了镜像总是与代码同步且由可信的官方环境构建
---
## 本章小结
| 功能 | 说明 |
|------|------|
| **官方镜像** | 优先使用的基础镜像 |
| **拉取限制** | 匿名 100/6h登录 200/6h |
| **安全** | 推荐开启 2FA 并使用 Access Token |
| **自动化** | 支持 Webhooks 和自动构建 |
## 延伸阅读
- [私有仓库](registry.md)搭建自己的 Registry
- [镜像加速器](../install/mirror.md)加速下载

View File

@@ -0,0 +1,126 @@
# Nexus 3
使用 Docker 官方的 Registry 创建的仓库面临一些维护问题比如某些镜像删除以后空间默认是不会回收的需要一些命令去回收空间然后重启 Registry在企业中把内部的一些工具包放入 `Nexus` 中是比较常见的做法最新版本 `Nexus3.x` 全面支持 Docker 的私有镜像所以使用 [`Nexus3.x`](https://www.sonatype.com/product/repository-oss-download) 一个软件来管理 `Docker` , `Maven` , `Yum` , `PyPI` 等是一个明智的选择。
## 启动 Nexus 容器
```bash
$ docker run -d --name nexus3 --restart=always \
-p 8081:8081 \
--mount src=nexus-data,target=/nexus-data \
sonatype/nexus3
```
首次运行需等待 3-5 分钟你可以使用 `docker logs nexus3 -f` 查看日志
```bash
$ docker logs nexus3 -f
2021-03-11 15:31:21,990+0000 INFO [jetty-main-1] *SYSTEM org.sonatype.nexus.bootstrap.jetty.JettyServer -
-------------------------------------------------
Started Sonatype Nexus OSS 3.30.0-01
-------------------------------------------------
```
如果你看到以上内容说明 `Nexus` 已经启动成功你可以使用浏览器打开 `http://YourIP:8081` 访问 `Nexus`
首次运行请通过以下命令获取初始密码
```bash
$ docker exec nexus3 cat /nexus-data/admin.password
9266139e-41a2-4abb-92ec-e4142a3532cb
```
首次启动 Nexus 的默认帐号是 `admin` 密码则是上边命令获取到的点击右上角登录首次登录需更改初始密码
登录之后可以点击页面上方的齿轮按钮按照下面的方法进行设置
## 创建仓库
创建一个私有仓库的方法 `Repository->Repositories` 点击右边菜单 `Create repository` 选择 `docker (hosted)`
* **Name**: 仓库的名称
* **HTTP**: 仓库单独的访问端口例如**5001**
* **Hosted -> Deployment pollcy**: 请选择 **Allow redeploy** 否则无法上传 Docker 镜像
其它的仓库创建方法请各位自己摸索还可以创建一个 `docker (proxy)` 类型的仓库链接到 DockerHub 再创建一个 `docker (group)` 类型的仓库把刚才的 `hosted` `proxy` 添加在一起主机在访问的时候默认下载私有仓库中的镜像如果没有将链接到 DockerHub 中下载并缓存到 Nexus
## 添加访问权限
菜单 `Security->Realms` Docker Bearer Token Realm 移到右边的框中保存
添加用户规则菜单 `Security->Roles`->`Create role` `Privlleges` 选项搜索 docker 把相应的规则移动到右边的框中然后保存
添加用户菜单 `Security->Users`->`Create local user` `Roles` 选项中选中刚才创建的规则移动到右边的窗口保存
## NGINX 加密代理
证书的生成请参见 [`私有仓库高级配置`](registry_auth.md) 里面证书生成一节
NGINX 示例配置如下
```nginx
upstream register
{
server "YourHostName OR IP":5001; #端口为上面添加私有镜像仓库时设置的 HTTP 选项的端口号
check interval=3000 rise=2 fall=10 timeout=1000 type=http;
check_http_send "HEAD / HTTP/1.0\r\n\r\n";
check_http_expect_alive http_4xx;
}
server {
server_name YourDomainName;#如果没有 DNS 服务器做解析,请删除此选项使用本机 IP 地址访问
listen 443 ssl;
ssl_certificate key/example.crt;
ssl_certificate_key key/example.key;
ssl_session_timeout 5m;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_ciphers HIGH:!aNULL:!MD5;
ssl_prefer_server_ciphers on;
large_client_header_buffers 4 32k;
client_max_body_size 300m;
client_body_buffer_size 512k;
proxy_connect_timeout 600;
proxy_read_timeout 600;
proxy_send_timeout 600;
proxy_buffer_size 128k;
proxy_buffers 4 64k;
proxy_busy_buffers_size 128k;
proxy_temp_file_write_size 512k;
location / {
proxy_set_header Host $host;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Port $server_port;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_redirect off;
proxy_set_header X-Real-IP $remote_addr;
proxy_pass http://register;
proxy_read_timeout 900s;
}
error_page 500 502 503 504 /50x.html;
}
```
## Docker 主机访问镜像仓库
如果不启用 SSL 加密可以通过 [前面章节](registry.md) 的方法添加非 https 仓库地址到 Docker 的配置文件中然后重启 Docker
使用 SSL 加密以后程序需要访问就不能采用修改配置的方式了具体方法如下
```bash
$ openssl s_client -showcerts -connect YourDomainName OR HostIP:443 </dev/null 2>/dev/null|openssl x509 -outform PEM >ca.crt
$ cat ca.crt | sudo tee -a /etc/ssl/certs/ca-certificates.crt
$ systemctl restart docker
```
使用 `docker login YourDomainName OR HostIP` 进行测试用户名密码填写上面 Nexus 中设置的

120
06_repository/registry.md Normal file
View File

@@ -0,0 +1,120 @@
# 私有仓库
有时候使用 Docker Hub 这样的公共仓库可能不方便用户可以创建一个本地仓库供私人使用
本节介绍如何使用本地仓库
[`docker-registry`](https://docs.docker.com/registry/) 是官方提供的工具,可以用于构建私有的镜像仓库。本文内容基于 [`docker-registry`](https://github.com/docker/distribution) v2.x 版本。
## 安装运行 docker-registry
### 容器运行
你可以使用官方 `registry` 镜像来运行
```bash
$ docker run -d -p 5000:5000 --restart=always --name registry registry
```
这将使用官方的 `registry` 镜像来启动私有仓库默认情况下仓库会被创建在容器的 `/var/lib/registry` 目录下你可以通过 `-v` 参数来将镜像文件存放在本地的指定路径例如下面的例子将上传的镜像放到本地的 `/opt/data/registry` 目录
```bash
$ docker run -d \
-p 5000:5000 \
-v /opt/data/registry:/var/lib/registry \
registry
```
## 在私有仓库上传搜索下载镜像
创建好私有仓库之后就可以使用 `docker tag` 来标记一个镜像然后推送它到仓库例如私有仓库地址为 `127.0.0.1:5000`
先在本机查看已有的镜像
```bash
$ docker image ls
REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE
ubuntu latest ba5877dc9bec 6 weeks ago 192.7 MB
```
使用 `docker tag` `ubuntu:latest` 这个镜像标记为 `127.0.0.1:5000/ubuntu:latest`
格式为 `docker tag IMAGE[:TAG] [REGISTRY_HOST[:REGISTRY_PORT]/]REPOSITORY[:TAG]`
```bash
$ docker tag ubuntu:latest 127.0.0.1:5000/ubuntu:latest
$ docker image ls
REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE
ubuntu latest ba5877dc9bec 6 weeks ago 192.7 MB
127.0.0.1:5000/ubuntu:latest latest ba5877dc9bec 6 weeks ago 192.7 MB
```
使用 `docker push` 上传标记的镜像
```bash
$ docker push 127.0.0.1:5000/ubuntu:latest
The push refers to repository [127.0.0.1:5000/ubuntu]
373a30c24545: Pushed
a9148f5200b0: Pushed
cdd3de0940ab: Pushed
fc56279bbb33: Pushed
b38367233d37: Pushed
2aebd096e0e2: Pushed
latest: digest: sha256:fe4277621f10b5026266932ddf760f5a756d2facd505a94d2da12f4f52f71f5a size: 1568
```
`curl` 查看仓库中的镜像
```bash
$ curl 127.0.0.1:5000/v2/_catalog
{"repositories":["ubuntu"]}
```
这里可以看到 `{"repositories":["ubuntu"]}`表明镜像已经被成功上传了
先删除已有镜像再尝试从私有仓库中下载这个镜像
```bash
$ docker image rm 127.0.0.1:5000/ubuntu:latest
$ docker pull 127.0.0.1:5000/ubuntu:latest
Pulling repository 127.0.0.1:5000/ubuntu:latest
ba5877dc9bec: Download complete
511136ea3c5a: Download complete
9bad880da3d2: Download complete
25f11f5fb0cb: Download complete
ebc34468f71d: Download complete
2318d26665ef: Download complete
$ docker image ls
REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE
127.0.0.1:5000/ubuntu:latest latest ba5877dc9bec 6 weeks ago 192.7 MB
```
## 配置非 https 仓库地址
如果你不想使用 `127.0.0.1:5000` 作为仓库地址比如想让本网段的其他主机也能把镜像推送到私有仓库你就得把例如 `192.168.199.100:5000` 这样的内网地址作为私有仓库地址这时你会发现无法成功推送镜像
这是因为 Docker 默认不允许非 `HTTPS` 方式推送镜像我们可以通过 Docker 的配置选项来取消这个限制或者查看下一节配置能够通过 `HTTPS` 访问的私有仓库
### Linux (systemd)
对于使用 `systemd` 的系统请在 `/etc/docker/daemon.json` 中写入如下内容如果文件不存在请新建该文件
```json
{
"registry-mirrors": [
"https://hub-mirror.c.163.com",
"https://mirror.baidubce.com"
],
"insecure-registries": [
"192.168.199.100:5000"
]
}
```
>注意该文件必须符合 `json` 规范否则 Docker 将不能启动
## 其他
对于 Docker Desktop for Windows Docker Desktop for Mac 在设置中的 `Docker Engine` 中进行编辑 增加和上边一样的字符串即可

View File

@@ -0,0 +1,217 @@
# 私有仓库高级配置
上一节我们搭建了一个具有基础功能的私有仓库本小节我们来使用 `Docker Compose` 搭建一个拥有权限认证TLS 的私有仓库
新建一个文件夹以下步骤均在该文件夹中进行
## 准备站点证书
如果你拥有一个域名国内各大云服务商均提供免费的站点证书你也可以使用 `openssl` 自行签发证书
这里假设我们将要搭建的私有仓库地址为 `docker.domain.com`下面我们介绍使用 `openssl` 自行签发 `docker.domain.com` 的站点 SSL 证书
第一步创建 `CA` 私钥
```bash
$ openssl genrsa -out "root-ca.key" 4096
```
第二步利用私钥创建 `CA` 根证书请求文件
```bash
$ openssl req \
-new -key "root-ca.key" \
-out "root-ca.csr" -sha256 \
-subj '/C=CN/ST=Shanxi/L=Datong/O=Your Company Name/CN=Your Company Name Docker Registry CA'
```
>以上命令中 `-subj` 参数里的 `/C` 表示国家 `CN``/ST` 表示省`/L` 表示城市或者地区`/O` 表示组织名`/CN` 通用名称
第三步配置 `CA` 根证书新建 `root-ca.cnf`
```bash
[root_ca]
basicConstraints = critical,CA:TRUE,pathlen:1
keyUsage = critical, nonRepudiation, cRLSign, keyCertSign
subjectKeyIdentifier=hash
```
第四步签发根证书
```bash
$ openssl x509 -req -days 3650 -in "root-ca.csr" \
-signkey "root-ca.key" -sha256 -out "root-ca.crt" \
-extfile "root-ca.cnf" -extensions \
root_ca
```
第五步生成站点 `SSL` 私钥
```bash
$ openssl genrsa -out "docker.domain.com.key" 4096
```
第六步使用私钥生成证书请求文件
```bash
$ openssl req -new -key "docker.domain.com.key" -out "site.csr" -sha256 \
-subj '/C=CN/ST=Shanxi/L=Datong/O=Your Company Name/CN=docker.domain.com'
```
第七步配置证书新建 `site.cnf` 文件
```bash
[server]
authorityKeyIdentifier=keyid,issuer
basicConstraints = critical,CA:FALSE
extendedKeyUsage=serverAuth
keyUsage = critical, digitalSignature, keyEncipherment
subjectAltName = DNS:docker.domain.com, IP:127.0.0.1
subjectKeyIdentifier=hash
```
第八步签署站点 `SSL` 证书
```bash
$ openssl x509 -req -days 750 -in "site.csr" -sha256 \
-CA "root-ca.crt" -CAkey "root-ca.key" -CAcreateserial \
-out "docker.domain.com.crt" -extfile "site.cnf" -extensions server
```
这样已经拥有了 `docker.domain.com` 的网站 SSL 私钥 `docker.domain.com.key` SSL 证书 `docker.domain.com.crt` CA 根证书 `root-ca.crt`
新建 `ssl` 文件夹并将 `docker.domain.com.key` `docker.domain.com.crt` `root-ca.crt` 这三个文件移入删除其他文件
## 配置私有仓库
私有仓库默认的配置文件位于 `/etc/docker/registry/config.yml`我们先在本地编辑 `config.yml`之后挂载到容器中
```yaml
log:
accesslog:
disabled: true
level: debug
formatter: text
fields:
service: registry
environment: staging
storage:
delete:
enabled: true
cache:
blobdescriptor: inmemory
filesystem:
rootdirectory: /var/lib/registry
auth:
htpasswd:
realm: basic-realm
path: /etc/docker/registry/auth/nginx.htpasswd
http:
addr: :443
host: https://docker.domain.com
headers:
X-Content-Type-Options: [nosniff]
http2:
disabled: false
tls:
certificate: /etc/docker/registry/ssl/docker.domain.com.crt
key: /etc/docker/registry/ssl/docker.domain.com.key
health:
storagedriver:
enabled: true
interval: 10s
threshold: 3
```
## 生成 http 认证文件
```bash
$ mkdir auth
$ docker run --rm \
--entrypoint htpasswd \
httpd:alpine \
-Bbn username password > auth/nginx.htpasswd
```
> 将上面的 `username` `password` 替换为你自己的用户名和密码
## 编辑 `docker-compose.yml`
```yaml
services:
registry:
image: registry
ports:
- "443:443"
volumes:
- ./:/etc/docker/registry
- registry-data:/var/lib/registry
volumes:
registry-data:
```
## 修改 hosts
编辑 `/etc/hosts`
```bash
127.0.0.1 docker.domain.com
```
## 启动
```bash
$ docker compose up -d
```
这样我们就搭建好了一个具有权限认证TLS 的私有仓库接下来我们测试其功能是否正常
## 测试私有仓库功能
由于自行签发的 CA 根证书不被系统信任所以我们需要将 CA 根证书 `ssl/root-ca.crt` 移入 `/etc/docker/certs.d/docker.domain.com` 文件夹中
```bash
$ sudo mkdir -p /etc/docker/certs.d/docker.domain.com
$ sudo cp ssl/root-ca.crt /etc/docker/certs.d/docker.domain.com/ca.crt
```
登录到私有仓库
```bash
$ docker login docker.domain.com
```
尝试推送拉取镜像
```bash
$ docker pull ubuntu:24.04
$ docker tag ubuntu:24.04 docker.domain.com/username/ubuntu:24.04
$ docker push docker.domain.com/username/ubuntu:24.04
$ docker image rm docker.domain.com/username/ubuntu:24.04
$ docker pull docker.domain.com/username/ubuntu:24.04
```
如果我们退出登录尝试推送镜像
```bash
$ docker logout docker.domain.com
$ docker push docker.domain.com/username/ubuntu:24.04
no basic auth credentials
```
发现会提示没有登录不能将镜像推送到私有仓库中
## 注意事项
如果你本机占用了 `443` 端口你可以配置 [Nginx 代理](https://docs.docker.com/registry/recipes/nginx/),这里不再赘述。