纯编程语言图像和 OS 加编程语言 docker 图像之间到底有什么区别?

Whats exactly the difference between a programming language only image and a OS plus programming language docker image?

在上次使用它很长一段时间后,我刚刚重新获取 Docker,我注意到 Docker 中心上的这两个变体,您可以从其中选择仅使用编程语言的图像(例如 node:11) 和编程语言加上 linux 发行版映像(如 node:11-alpine),所以我想知道在 运行 时间这两者之间有什么区别,我的意思是,编程语言只有映像会靠宿主OS到运行?或者我必须始终下载包含 OS 的图像才能使其正确 运行?

让我们使用 node Docker images.

来澄清一些困惑

当你对一些没有 -linux-distro 前缀的 node:versiondocker pull 时,它 意味着它不有一个 OS(或工作环境)并且只有“包含 OS 的图像”才能正确 运行。它通常只是意味着你,作为这个镜像的用户,不关心基础镜像是什么或者基础 Linux 发行版是什么,你只是想尽快容器化你的工作应用程序而不需要做额外的工作(例如要安装的额外东西等)。

如果您查看 支持的标签和相应的 Dockerfile 链接 部分 node images,您会发现 node:version 图像仍然只是别名一个特定的 node:version-linux-distro。例如,对于 node:14.15.4:

如果您尝试拉取它们,它们会引用相同的图像:

~$ docker pull node:14.15.4
14.15.4: Pulling from library/node
2587235a7635: Pull complete 
953fe5c215cb: Pull complete 
....
Digest: sha256:04a33dac55af8d3170bffc91ca31fe8000b96ae1bab1a090deb920ca2ca2a38e
Status: Downloaded newer image for node:14.15.4
docker.io/library/node:14.15.4

~$ docker pull node:14.15.4-stretch
14.15.4-stretch: Pulling from library/node
Digest: sha256:04a33dac55af8d3170bffc91ca31fe8000b96ae1bab1a090deb920ca2ca2a38e
Status: Downloaded newer image for node:14.15.4-stretch
docker.io/library/node:14.15.4-stretch

node:14.15.4node:14.15.4-stretch 具有相同的摘要

04a33dac55af8d3170bffc91ca31fe8000b96ae1bab1a090deb920ca2ca2a38e

...它们也是从 same Dockerfile. You can also try :

生成的
~$ docker inspect --format='{{.RootFS}}' node:14.15.4 > node.14.15.4.txt
~$ docker inspect --format='{{.RootFS}}' node:14.15.4-stretch > node.14.15.4-stretch.txt
~$ diff --brief node.14.15.4.txt node.14.15.4-stretch.txt 

...而且没有区别。如果您仍然认为 node:14.15.4 没有 OS,运行 并检查:

~$ docker run -it node:14.15.4 bash
root@942ea36068d9:/# cat /etc/os-release 
PRETTY_NAME="Debian GNU/Linux 9 (stretch)"
NAME="Debian GNU/Linux"
VERSION_ID="9"
VERSION="9 (stretch)"
VERSION_CODENAME=stretch
ID=debian
HOME_URL="https://www.debian.org/"
SUPPORT_URL="https://www.debian.org/support"
BUG_REPORT_URL="https://bugs.debian.org/

~$ docker run -it node:14.15.4-stretch bash
root@d504a57244eb:/# cat /etc/os-release
PRETTY_NAME="Debian GNU/Linux 9 (stretch)"
NAME="Debian GNU/Linux"
VERSION_ID="9"
VERSION="9 (stretch)"
VERSION_CODENAME=stretch
ID=debian
HOME_URL="https://www.debian.org/"
SUPPORT_URL="https://www.debian.org/support"
BUG_REPORT_URL="https://bugs.debian.org/"

...并且看到它们 node:14.15.4 也是使用 Debian Stretch 作为其基础映像构建的(技术上它是 buildpack-deps:stretch 如果您检查 Dockerfile)。

这适用于其他“编程语言”图像,例如 ruby and python。因此,要回答您的问题,当您使用未指定 Linux 发行版的图像时,应该没有任何区别。它是为那些不想关心 Linux 使用了什么发行版,并且想要立即 可用 的人准备的。

与名称中包含 Linux 发行版的图像相关的问题是“我应该使用哪个 Linux 发行版?”。

对于 node 图像,在其 Dockerhub page图像变体 部分中进行了解释。引用 node:<version> 的那个(没有 Linux 发行版的那个):

This is the defacto image. If you are unsure about what your needs are, you probably want to use this one. It is designed to be used both as a throw away container (mount your source code and start the container to start your app), as well as the base to build other images off of.

...

This tag is based off of buildpack-deps. buildpack-deps is designed for the average user of Docker who has many images on their system. It, by design, has a large number of extremely common Debian packages. This reduces the number of packages that images that derive from it need to install, thus reducing the overall size of all images on your system.

请注意有关已预安装许多软件包的部分。通常,这意味着如果您不基于此图像构建和发布自己的应用程序图像,或者您不关心图像的最终大小(例如磁​​盘 space 不是问题),或者如果您没有 CI/CD 将图像 to/from 拉入和推送到某处的管道,那么您始终可以从这种类型的图像开始。

-alpine-slim 通常用于减小图像的大小,但是 它们通常需要更多的工作才能安装你需要的东西(其他图像中预装的东西)。再次查看 Image Variants 部分,了解为什么以及何时需要它们。您还可以查看相关的 SO post: .