Sunday, March 7, 2010

what's good about conary

试图总结一下 conary 到底有什么独特之处... 不过我对其他的包管理不是很熟悉,所以不太好总结。

这样,以下内容基本上是这篇文章的意译。

包管理,也就是管理系统上所有其他软件的一个软件。但 conary 不只是一个包管理软件,更是一个强大的对软件系统的版本管理系统。

===========
第一个问题,如何组织软件源(repository)

在 deb/rpm 系统上,一个 repository 无非是某个服务器上的一个目录,其中存放着软件包(一些文件)。文件的命名无非就是"软件名",加上"软件版本"(当然一般还有其他部分,稍后再提)。

问题来自于文件的命名是任意的,手动的。比如有两个软件源,都提供了firefox-3.0 这个包,那么包管理就会搜索到两个"相同"的包,可能产生冲突。

而 conary 不这样处理软件源,conary 的 repository 并不是一个静态的目录,而是一个有版本的动态的分支。整个软件源都是处在版本控制下的,随着其中软件的更新,不断的向前发展,而不是像磁盘文件系统上的一个目录,新版本的文件会覆盖旧文件。

当然,conary 里面的包名字也必须有好几个部分,比如名字加版本。但这些都是由 conary 自动管理,没有手动的过程,conary 能保证两个不同的包,用户能识别出它们确实是不一样的。比如有两个 deb 的源,apt.joeschmoe.com 和 apt.joesmith.com,它们有同一个版本的 liferea,那包名可能是一样的,就会有问题,而 conary 不会遇到这个矛盾,因为,软件源的域名其实也是包名字的一部分。

如果 deb 要以域名来辨别不同的包,那只能把域名写到文件名里面,结果必然是,软件包的名字变得特别长。正因为 conary 下的“包”并不是以文件形式存在的,才能做到上边这一点。

而问题没有到此为止,一般发行版会支持多个硬件平台 (至少有 32 位或 64 位之分吧)。deb/rpm 的做法是什么?只能把 arch 写进文件名里面。结果就是这样的,liferea-1.2.2-2.el5.rf.x86_64.rpm。能看出跟 liferea-1.2.2-2.el5.rf.x86-64.rpm 的区别吗?

conary 也需要支持不用的 arch,包名字也会包含 x86, x86_64 等等。但由于 conary 的“自动管理”,默认情况下这些额外信息是被隐藏的。有时候一个简单的"liferea"就能识别一个包,有时候需要 "liferea=1.0"才能识别, 有时候需要 "liferea=foresight.rpath.org@fl:2-devel" (以区别 "liferea=foresight.rpath.org@fl:2-qa", 或者 "liferea=jesse.rpath.org@fl:2-devel"),有时候甚至需要"liferea=foresight.rpath.org@fl:2-devel/1.7.3-0.1-2",而这就是 conary 里面包的 full-name 的样子。

===========
正由于以上这些,conary 不需要复杂的 sources.list。如果你想从我的个人软件源安装 liferea,在 deb 世界里需要把我的源添加到 sources.list 里边,这样 apt 才能自动从那里查找更新。

而对于 conay, 只需要安装 liferea=jesse.rpath.org@fl:2-devel,conary 会记住这个源,以后只会从这里查找更新,即使 foresight 的官方源里面有更新的版本,也不会影响你的系统。

===========
细粒度的依赖关系

解决依赖是包管理的另一个基本作用,对于 deb/rpm 来说,依赖是定义在包的层面的,带来的一个问题是,有时候要安装某个包,需要先安装一系列的依赖,它们的体积加起来可能很大。另一个问题是,更新的时候,整个包都要重新下载,而好多时候这是不需要的,比如 man page 和一些图片,可能并没有任何变化。

conary 是在文件层次上解决依赖的,所以,一个包并不依赖于另"一个包",而是依赖某个文件的存在。conary 把包划分成几个部分,比如 :runtime, :doc, 或者 :devel,安装依赖包、更新包都是基于这个子部分的,用不到或没有变化的部分就不用下载。好处是可以节省带宽,节省硬盘空间,节省电力,节省能源...

而且这带来了另一个可能:系统可以定制得很小,能够把不需要的都删掉。比如最近我们在裁减 GNOME Developer Kit 的大小,在脚本里有这一句:

        r.removeComponents(['doc', 'supdoc', 'build-tree', 'devellib', 'devel'],
            'group-gnome-dist')

这样就把所有的文档、开发相关的文件移除了。

当然,deb 和 rpm 也能把一个包划分开 (也就是那些 -devel 包的由来)。问题是,手动。打包的开发者必须在 spec 文件里手动指明哪些文件是 liferea-doc 的,哪些是 liferea-devel 包的。但 conary 能自动完成这些,安装到 /etc 的,一般就是 :config 部分的;在 /user/share/man/ 下的,应该就是 :doc。conary 能识别出 general case 来,开发者只需要做剩下的那一点。

===========
回滚。由于整个系统都是在 conary 的版本管理之下,所以 conary 支持包管理操作的回滚。这个特性是最容易记住的,所以不细说了。

===========
给 conary 打包非常容易,所有的打包过程,都由简短的 python 脚本定义。在我看来,比 rpm 的 spec 文件清晰的多。而且像前面提到的,一般来说,开发者只处理特殊情况就行了,负担会大大减小。

===========
所以,无论对用户还是对开发者,conary 都是个不错的选择。

现在对用户存在的一个大问题呢,就是 conary 还缺少一个足够简单、但又能发挥其威力的前端,PackageKit 是当前的选择,但是还有很多的工作要做。

想进一步了解的话,请登陆 #foresight (freenode)。
blog comments powered by Disqus