如何获取镜像构建ID并在Dockerfile的FROM指令中指定?
为什么指定了具体Python版本的Docker镜像,构建结果还是会不一样?
很多人写Dockerfile时,都会觉得用FROM python:3.6.4这种明确指定版本的指令,就能保证每次在新环境里执行docker build时,出来的镜像完全一致,但实际情况往往会打破这个认知。
就像你遇到的场景:两天前写的Dockerfile,当时构建的镜像里用apt-get安装的软件包都是当时的版本,但如果现在再跑一次构建,结果很可能就不一样了。这主要有两个核心原因:
- 基础镜像并非一成不变:虽然你指定了
3.6.4这个标签,但官方镜像的维护者会在同一个标签下更新镜像内容——比如修复系统级的安全漏洞、更新底层Debian/Ubuntu的默认软件包版本等。也就是说,python:3.6.4这个标签对应的镜像,今天和两天前的内容可能已经不一样了。 - 构建时的外部依赖会变动:如果你的Dockerfile里有
apt-get install或者pip install这类命令,这些包的源(比如PyPI、系统软件源)里的包版本是会更新的。哪怕基础镜像没变化,拉到的依赖包版本不同,最终镜像也会有差异。
想要解决这个问题,保证构建的一致性,这里有几个实用的方案:
- 用镜像摘要锁定基础镜像:不要依赖标签,改用镜像的唯一SHA-256摘要来指定基础镜像,比如
FROM python@sha256:abcdef123456...。摘要是镜像的唯一标识,只要摘要不变,拉取的镜像就绝对和之前的一样。 - 固定所有依赖的版本:不管是
pip还是apt-get,都明确指定具体版本。比如pip install requests==2.28.1,或者apt-get install -y nginx=1.18.0-0ubuntu1,避免自动拉取最新版本。 - 离线构建或缓存依赖:把需要的系统包、Python包提前下载到本地,构建时从本地复制到镜像里,完全脱离外部源的影响,从根源上避免版本变动。
内容的提问来源于stack exchange,提问作者Kirill Bulygin
相关产品推荐
相关产品推荐

