修补软件包
本文介绍如何在 Arch 构建系统 (ABS) 中创建软件包补丁以及如何应用补丁。
补丁描述了一个或多个文件的行更改集合。补丁通常用于自动化源代码的更改。
创建补丁
diff 工具逐行比较文件。如果您保存其输出,您就得到了一个补丁,例如 diff --unified --recursive --text foo bar > foobar.patch
(可以缩短为 diff -ura
)。如果您传递目录,diff 将比较它们包含的文件。
- 如果您已经构建了软件包,请删除
src
目录。 - 运行
makepkg --nobuild
/makepkg -o
,它将下载并提取PKGBUILD
中指定的源文件,但不会构建它们。如果您在其上制作补丁的系统没有所需的依赖项,您可能必须运行makepkg --nobuild --nodeps
/makepkg -od
来代替。 - 在
src
目录中创建提取目录的两个副本,一个作为原始副本,另一个用于您的更改版本。我们将它们称为package.orig
和package.new
。 - 在
package.new
目录中进行更改。 - 运行
diff -ura package.orig package.new --color
并检查补丁是否看起来不错。 - 运行
diff -ura package.orig package.new > package.patch
以创建补丁。 - 进入您从中复制的初始
package.orig
目录,并使用patch --strip=1 --input=../package.patch
(可以缩短为patch -p1 -i ../package.patch
)应用补丁。通过使用makepkg --noextract --install
/makepkg -ei
构建和安装修改后的软件包来验证补丁是否有效。
有关更多信息,请参阅 diff(1) 和 git-diff(1)。
.patch
来为特定提交或特定合并/拉取请求生成补丁。对于 GitHub,还请考虑在 URL 末尾添加 ?full_index=1
参数,以避免因将来对象哈希长度的更改而导致的校验和不匹配。应用补丁
本节概述如何从 PKGBUILD
的 prepare()
函数中应用您创建的或从 Internet 下载的补丁。请按照以下步骤操作
- 在
PKGBUILD
的source
数组中为补丁文件添加一个条目,与原始源 URL 用空格分隔。如果该文件在线可用,您可以提供完整的 URL,它将自动下载并放置在src
目录中。如果是您自己创建的补丁,或者以其他方式不可用,您应该将补丁文件放在与PKGBUILD
文件相同的目录中,并且只需将文件名添加到 source 数组中,以便将其复制到src
目录中。如果您重新分发PKGBUILD
,您当然应该将补丁与PKGBUILD
一起包含在内。 - 然后使用
makepkg -g >> PKGBUILD
或updpkgsums
(来自 pacman-contrib)来更新sha512sums
数组。或者手动向sha512sums
数组添加条目;您可以使用 sha512sum 工具生成补丁的总和。 - 如果
PKGBUILD
中尚不存在prepare()
函数,请创建它。 - 第一步是进入需要修补的目录(在
prepare()
函数中,而不是在您的终端上!您想要自动化应用补丁的过程)。您可以使用类似cd $pkgname-$pkgver
的命令来执行此操作。$pkgname-$pkgver
通常是通过解压下载的源文件创建的目录的名称,但并非在所有情况下都是如此。 - 现在您只需从此目录中应用补丁。这可以通过将
patch -p1 -i pkgname.patch
添加到您的prepare()
函数中来非常简单地完成,将pkgname.patch
更改为包含 diff 的文件的名称(该文件已自动复制到您的src
目录中,因为它在PKGBUILD
文件的source
数组中)。
一个 prepare 函数示例
prepare() { cd $pkgname-$pkgver patch -Np1 -i ../eject.patch }
或者,您可以使用 patch
的 --directory
/-d
标志,而无需先使用 cd。上面的示例将变为
prepare() { patch -d $pkgname-$pkgver -Np1 -i ../eject.patch }
现在从终端运行 makepkg
。如果一切顺利,补丁将自动应用,并且您的新软件包将包含补丁中包含的任何更改。如果不是,您可能必须尝试使用 patch 的 --strip
/-p
选项。在实验时,您可能会发现 --dry-run
、--reverse
或 --verbose
选项可用。阅读 patch(1) 以获取更多信息。
基本上,它的工作原理如下。如果 diff 文件是为将补丁应用于 myversion/
中的文件而创建的,则 diff 文件将应用于 myversion/file
。您正在从 yourversion/
目录中运行它(因为您将在 PKGBUILD
中 cd 进入该目录),因此当 patch 应用文件时,您希望将其应用于文件 file
,去掉 myversion/
部分。-p1
通过从路径中删除一个目录来做到这一点。但是,如果开发人员在 myfiles/myversion
中打补丁,则需要删除两个目录,因此您使用 -p2
。
如果您不应用 -p
选项,它将删除所有目录结构。如果所有文件都在基本目录中,这没问题,但是如果补丁是在 myversion/
上创建的,并且其中一个编辑的文件是 myversion/src/file
,并且您从 yourversion
中运行没有 -p
选项的补丁,它将尝试修补名为 yourversion/file
的文件。
大多数开发人员从正在修补的目录的父目录创建补丁,因此 -p1
通常是正确的。
使用 quilt
一种更简单的创建补丁的方法是使用 quilt,它为管理许多补丁提供了更好的支持,例如应用补丁、刷新补丁以及将已修补的文件恢复到原始状态。quilt 在 Debian 上用于管理他们的补丁。有关生成、应用补丁和恢复已修补文件的基本 quilt 用法的基本信息,请参阅 Using Quilt。
参见
- http://www.kegel.com/academy/opensource.html — 关于修补文件的有用信息