Docker的诅咒

此文为原文的中文翻译,来自InfoQ 作者 | J. B. Crawford 译者 | 核子可乐 策划 | 褚杏娟 GitLab 高级专业服务工程师、DevOps 顾问 J. B. Crawford 最近写了一篇关于抱怨 Docker 的文章,在网上引发了开发者们的讨论。有人力挺,也有人反对:“我不明白没有 Docker 的堆栈管理怎么会更好。” J. B. Crawford 在文章中表示:“我不太确定 Docker 帮助节约的时间有没有超过对它的管理成本。”下面让我们具体看看他为什么对 Docker 感到不满。 系统管理中的基础问题 打包软件一直是系统管理中的一大基础问题。它非常重要,对系统的使用方式有着巨大影响,甚至让包管理器成为区分操作系统的一项重要指标。 以 Windows 为例:在很多“Linux 派”眼中,这款操作系统最不讨喜的就是缺乏包管理机制,微软先后多次尝试引入这个概念也都没能得到广泛认可。相比之下,Linux 世界中各发行版间的主要区别,就集中在其管理软件 repo 的方式上。我所指的不只是 dpkb 和 rpm 之间的差异,而是在强调更底层的设计,例如硬性指定还是上游配置、稳定 repo 还是滚动发布。拿 RHEL 和 Arch 来说,二者虽然共享绝大多数实现,但管理风格却截然不同。 大多数 Linux 发行版都会明确强调某种软件应该如何打包(甚至规定了多久打包一次),而且这些系统也都有着一项共通理念:将依赖项集中起来。应该把库声明为依赖项,并把所依赖的包安装在公共位置以供链接器使用。但这也可能带来挑战,因为不同的软件往往依赖于不同的库版本,而各版本之间可能并不兼容。这也是在维护 Linux 发行版时最典型的老大难问题:如何提供能够良好协作的软件 repo 版本。像 RHEL 这类稳定发行版的一大优势,就是它们在这方面表现得相当可靠;至于缺点,就是这种可靠性其实是通过拒绝大部分新版本软件来实现的。 由于需要提供大量可以相互兼容的软件版本,并确保发行版遵守各种构建规范(例如支持自由软件等开发理念、以及配置文件布局等具体规则),所以向 Linux 发行版引入新软件时往往极度麻烦且繁琐。对于软件维护人员来说,他们需要面对一大堆有着特定构建和配置差异的旧版本,并想办法把它们塞进发行版中去。而在发行版和软件包维护者这边,则需要全盘考虑各种上游软件是否符合发行版策略,并解决版本和依赖项问题。虽然行业中已经出台了一系列相关规范,但具体操作仍然令人头痛,庞大的工作量也几近疯狂。 这就形成了一种双输的诡异局面:希望自己的软件能够广泛传播的开发者必须忍受发行版的怪癖,而想要壮大自身软件生态的发行版也得顺应开发者。每个人都不开心,每个人都很疲惫。 有问题,自然有人尝试解决。业界已经在这方面做出了各种探索,但也正是因为方法多种多样,所以至今没有真正出现一种能够统领全局的解决方案。在桌面环境中,常见的软件分发选项有 Flatpak、Snap 和 AppImage 等。这些系统的镜像或应用程序能够将软件及其依赖项共同打包,提供一套完整的独立环境,从而保证在任何发行版上都能正常工作。 但在实际使用时,我自己曾不止一次对 flatpak 文件进行逆向工程以修改其中的依赖项,所以说上述工具的宣传效果在日常应用时并不一定能发挥作用。但公平地讲,软件在与各种要素的交互过程中,难免会出现意料之外的状况——比如运行时无法正确将各种要素彼此隔离开来。视频技术栈就是个典型,我们往往需要删除或替换掉包中错误的 OpenGL 库,才能使其跟特定图形驱动程序共同运行。 ...

December 30, 2023 · 2 min · Me