为什么 Debian 是这样的?

Table of Contents

原文:https://blog.liw.fi/posts/2023/debian-reasons/

Debian 是个庞大而复杂的操作系统,同时也是个庞大的开源项目,目前都已经三十年的历史了。对于一些用户而言,它的某些方面很奇怪。但是大多数这样的事情都有原因的,但又很难找出原因是什么。本文试图回答其中一些这样的问题,但并不详细介绍该项目的历史。

1. Debian 想要成为什么

Debian 希望成为一个高质量、安全的通用操作系统,并且只包含自由和开源软件,同时能运行在世界上大多数正在使用的计算机上。

我所说的“通用”是指 Debian 应该适合大多数人的大多数用途。虽然不管出于什么原因,总会有一些不太合适的情况,但这是一个很好的目标。其它的一些发行版一般都有特定的目的:桌面、服务器、玩游戏、做科研等等。其实以通用目的或特定目的都可以,但是,不同的目标选择就会导致一路上做出一些不同的决策。

对于 Debian 来说,“通用”就意味着 Debian 不会根据软件的用途来打包。Debian 在这里做出真正的唯一选择是软件是否自由,以及 Debian 是否能维护一个高质量的软件包。

2. 宪法、权力结构、治理

Debian 是个非常明确的民主开源组织。它有明确的决策流程、每年选举出一名项目领导人。此外,项目领导人的权力严格受限,多数与领导相关的权力都被明确授予给了其他人。

这里说下历史背景,最初的 Debian 项目领导人在选择下台之前都是隐性的全能独裁者。后来,一位项目领导人太过分,一场叛乱把他们赶出去了,于是引入了民主制度。作为其中的一部分,项目有了正式的宪章,并制定了规则。

Debian 之所以有这样的规则,是因为更少的规则和更少的官僚主义在 Debian 的早期历史中是行不通的。

3. 社会契约和 Debian 自由软件指南

20 世纪 90 年代中期,在引入“开源”这个术语以前,自由软件基金会定义了什么是“自由软件”,但其中又有很多需要解释的地方。Debian 希望有更清晰的规则,所以提出了 Debian 自由软件指南,并将其作为其社会契约的一部分。

“社会契约”是 Debian 对自己和全世界关于 Debian 是什么以及做什么的承诺。DFSG(Debian Free Software Guidelines)也是其中的一部分。这是 Debian 的基础文档,并且有意地使它在 Debian 章程中难以更改。

更详细的规则使 Debian 将接受的内容更加明确,也简化了相关的讨论。当然,也还是有很多东西需要讨论。

DFSG 后来成为开源定义的基础。

4. 独立一体

Debian 坚持独立一体。任何由 Debian 打包的 Debian 软件,都必须仅使用 Debian 的依赖项进行构建(编译)。同样,Debian 中的所有内容都必须由 Debian 来构建。这会造成大量额外工作。例如,当前的编程语言工具通常假定它可以在构建时从在线资源库中下载依赖,这对于 Debian 来说是不可接受的。

其主要原因是依赖项以后可能会变得不可用。Debian 又没法控制第三方软件包的仓库,如果某个软件包或连整个仓库都消失了,Debian 就没法重建该软件包了。Debian 需要重建软件包来升级到新的编译器、修复安全问题、移植到新的体系结构,或者只是对软件包进行一些修改,包括修复 Bug。

如果 Debian 不是独立一体的,当需要发布紧急的安全修复时,它就会被数以万计的软件包及其所有依赖包所左右。这点是 Debian 无法接受的,因此 Debian 选择把所有的依赖都打包了。

当然,对于 Debian 来说,这就意味着打包某些东西要做大量的工作。

5. 无捆绑库

Debian 避免使用与软件包捆绑在一起的库副本及依赖。许多上游项目发现捆绑或“vendor”依赖关系更容易,但对 Debian 而言,这意味着一些流行库就会存在多个副本。当要修复此类库中的安全问题或其他严重问题时,就必须得找到所有的副本,然后逐一修复它们。这是一项繁重的工作,而且如果安全问题十分紧急时,这样搞会浪费时间。

举个例子:zlib 被大量项目使用。根据性质,它需要处理的数据可能是包含了恶意内容,用来利用库里的某个漏洞。这种情况曾有发生过。有一次,Debian 在存档中找到了数十个捆绑了 zlib 副本的包,然后花费了大量精力来确保 Debian 中的软件包只用了打包版本的 zlib。

因此,Debian 选择在打包软件时提前做好工作,只为了确保 Debian 中的包只使用 Debian 中打包的库的版本。

上游开发人员并不总是喜欢这样搞,因为他们更希望只需要处理他们捆绑的库版本。这也是他们验证自己软件的版本。有时会导致与 Debian 发生摩擦。

6. 会员流程

鉴于 Debian 操作系统的规模和复杂性,以及它的流行程度,项目需要信任成员,尤其是要信任上传新软件包的人。由于 20 世纪 90 年代 Linux 的技术限制,每个 Debian 软件包在安装过程中都有完全的 root 访问权限。换句话说,每位 Debian 开发者都有可能成为任一台运行了 Debian 机器的 root 用户。由于运行了 Debian 的机器数以千万计,这就意味着潜在的高权限带来的威胁。

Debian 以各种方式来审查新成员。理想情况下,每位新成员都需要先加入 Debian 开发社区足够长的时间,让其他人所熟知,并且在社区内建立了信任。

对于那些想要加入 Debian 的人来说,这个过程可能会令人沮丧,尤其是对于那些习惯了较小的开源项目。

7. 发布代号

Debian 给每个主版本都分配了一个代号,当初的目的是为了降低镜像 Debian 软件包归档的成本。

20 世纪 90 年代中期,在 Debian 1.0 即将发布时还未使用代号。相反,每个版本都有一个以版本命名目录的归档。由于开发新版本需要一段时间,所以就提前创建了“1.0”目录。很不幸,在 Debian 真正完成 1.0 前,一家 CD-ROM 发行商过早地批量生产了他们标记为 1.0 的光盘。这就意味着获得 Debian 1.0 CD-ROM 的人获得的实际上不是 1.0。

为了避免这种情况再次发生,一个明显的解决方案是把准备发布的内容放到名为“1.0-not-released”的目录中,发布后再把目录重命名为“1.0”。但是,当更改了目录名时,所有镜像都必须重新下载该版本。考虑到 Debian 的巨大规模(数百个软件包!数十兆字节!),这将是昂贵的代价。因此,Debian 选择使用代号。

后来,“pool”结构被添加到 Debian 归档中。这样,所有版本的文件都位于同一目录树中,元数据文件指定哪些文件属于每个版本,这使得镜像更容易。现在也许可以放弃代号,换成版本号,但我不知道 Debian 是否对此感兴趣。

8. 更改很缓慢

正如上面所说的,Debian 非常庞大,一点也不小。

大船停得很慢,大型项目也变化缓慢。Debian 中任何影响到大部分软件包的变化都可能需要数百名志愿者来完成。这不会很快发生。

有时,只需少数人就能完成工作,而 Debian 有相应的流程来实现这一点。例如,如果上传了新版本的 GNU C 编译器,那么找出其他软件包中需要修正的地方的工作通常只需要几个人就能完成。

改变通常需要时间,因为需要建立共识就需要广泛的讨论。这需要时间,而且时间都不短。

也意味着 Debian 开发人员在技术决策上往往比较保守,他们往往更倾向不需要大规模做更改的解决方案。