docker

关注公众号 jb51net

关闭
首页 > 网站技巧 > 服务器 > 云和虚拟化 > docker > Docker拉取镜像部分成功部分失败

Docker拉取镜像部分成功部分失败的解决方案

作者:mr.Darker

最近在部署 Zitadel 身份认证平台的过程中,遇到一个看似“随机”的问题:Docker 有些镜像可以拉取,有些却一直超时失败,最终通过配置 Docker 守护进程级别的代理 才解决,文章记录整个问题分析和解决过程,便于自己和大家后期参考,需要的朋友可以参考下

 问题背景

部署 Zitadel 时,使用官方提供的 getting-started-with-zitadel.sh 脚本,脚本会拉取多个 Docker 镜像,比如:

问题表现

在执行过程中,有些镜像可以拉取成功,有些会报如下错误:

Error response from daemon: Get "https://registry-1.docker.io/v2/": 
net/http: request canceled while waiting for connection 
(Client.Timeout exceeded while awaiting headers)

观察结果是:

镜像是否拉取成功
ghcr.io/zitadel/zitadel✅ 成功
docker.io/library/caddy✅ 成功
netbirdio/management / netbirdio/signal❌ 超时失败

同时,我们很早就配置了一些 Docker Hub 镜像加速器(如阿里云,腾讯云,DaoCloud 等),这也是为什么有些镜像能顺利拉取,有些却不能的原因之一。

因为镜像加速器仅能加速“Docker Hub 官方镜像”,如 library/nginx 或 docker.io/library/caddy,而像 netbirdio/* 这种非官方项目的镜像并不在加速器白名单内,因此仍然会拉取失败。

初步排查

网络本身没有问题

但 Docker 拉取仍旧失败

通过多次测试发现,Docker 有些镜像拉得飞快,有些镜像卡死或超时,尤其是 docker.io/netbirdio 相关的镜像。

这时开始怀疑:

可能和代理有关

解决思路:配置 Docker 的守护进程代理

平时我们习惯配置终端代理,例如:

export http_proxy=http://127.0.0.1:7890
export https_proxy=http://127.0.0.1:7890

但实际上:

Docker 守护进程(dockerd)是独立运行的,它不会继承当前 shell 的代理环境变量!

解决方案:配置 Docker 的 systemd 代理

sudo mkdir -p /etc/systemd/system/docker.service.d
sudo nano /etc/systemd/system/docker.service.d/http-proxy.conf
[Service]
Environment="HTTP_PROXY=http://127.0.0.1:7890"
Environment="HTTPS_PROXY=http://127.0.0.1:7890"
Environment="NO_PROXY=localhost,127.0.0.1,.corp"
sudo systemctl daemon-reexec
sudo systemctl daemon-reload
sudo systemctl restart docker
sudo systemctl show --property=Environment docker

输出应该包含你刚才设置的代理环境变量。

最终结果

重启 Docker 后再次运行部署脚本:

总结

问题结论
Docker 部分镜像拉取失败是由于 Docker 守护进程未配置代理,而不是网络本身问题
解决方案配置 systemd 层面的 http-proxy.conf,让 dockerd 使用代理
验证方式systemctl show --property=Environment docker 查看生效状态

经验教训

以上就是Docker拉取镜像部分成功部分失败的解决方案的详细内容,更多关于Docker拉取镜像部分成功部分失败的资料请关注脚本之家其它相关文章!

您可能感兴趣的文章:
阅读全文