rpm 升级不能用文件替换目录?
rpm upgrade can't replace directory with file?
我维护了一个以前版本的包,其中包含一个包含文件的子目录。升级发生在 RHEL/CentOS 7。例如我的版本 1.0 RPM 包含:
/opt/foo/etc/bar/x/y
/opt/foo/etc/bar/z
等在此包的较新版本中,我必须用同名文件替换整个 /opt/foo/etc/bar
目录(不幸的是,该工具需要这样做,对此我无能为力)。所以在新版本的包中,会包含
/opt/foo/etc/bar
这是一个文件。
如果我 运行 正常 rpm --upgrade pkg-2.0.rpm
,我什至在调用任何规范脚本之前就收到错误消息:
file /opt/foo/etc/bar from install of pkg-2.0-1.x86_64 conflicts with file from package pkg-1.0-1.x86_64
为了避免这种情况,我必须在我的 rpm
命令行中添加 --replacefiles
选项,这很糟糕。
即使我这样做了,它仍然失败了,这次是在我的 preinst scriptlet 运行s 之后,出现如下错误:
error: unpacking of archive failed on file /opt/foo/etc/bar: cpio: rename failed - Is a directory
error: pkg-2.0-1.x86_64: install failed
error: pkg-1.0-1.x86_64: erase skipped
据我所知,我能做到这一点的唯一方法是修改我的 preinst 以删除目录,并将 --replacefiles
选项添加到 rpm
。即使在我完成所有这些之后,虽然升级确实成功了,但它会为 "missing" (因为我删除了目录)的每个文件发出警告:
warning: file /opt/foo/etc/bar/x/y: remove failed: Not a directory
warning: file /opt/foo/etc/bar/z: remove failed: Not a directory
我不知道为什么会显示此错误,因为这些东西 不是 目录而且从来都不是,但无论如何。
我到处搜索关于这个特定问题的信息,虽然我发现了很多类似的错误,但它们都是针对不同情况的,例如人们试图安装两个文件重叠或类似的包.在这里,我肯定会尝试将一个版本的软件包升级到同一软件包的新版本。
似乎没有办法让这个在 RPM 中干净地工作;这只是 RPM 工具的缺陷还是我遗漏了什么?
这是rpm一直以来的突出问题。这是由CPIO引起的,它不能用文件替换目录(反之亦然)。
如果您不能更改路径名,那么您有两个选择 - 都是丑陋的技巧:
您从 A-1.0.rpm 开始,其中包括 /opt/foo/etc/bar/z
作为目录。然后你创建 A-transition-1.1.rpm 没有 /opt/foo/etc/bar/z
目录(事实上 - 它可以是空包)并且你将 Obsolete: A <= 0:1.0
。前导零是纪元。我假设你过去没有使用过它。然后您将创建新的 A-1.0.rpm 和 Epoch: 1
并且您将 Obsolete: A-transition < 0:2.0
并且这次它可以包含 /opt/foo/etc/bar/z
作为文件。 RPM 将进行升级 0:A-1.0 -> A-transition -> 1:A-1.0
因为这是一个 CPIO 问题,您可以:
%pre
如果 [ -d /opt/foo/etc/bar/z ];然后
rm -rf /opt/foo/etc/bar/z
fi
RPM 会在删除旧包时大喊缺少 /opt/foo/etc/bar/z
,但它应该会通过(你没有测试过)。
我维护了一个以前版本的包,其中包含一个包含文件的子目录。升级发生在 RHEL/CentOS 7。例如我的版本 1.0 RPM 包含:
/opt/foo/etc/bar/x/y
/opt/foo/etc/bar/z
等在此包的较新版本中,我必须用同名文件替换整个 /opt/foo/etc/bar
目录(不幸的是,该工具需要这样做,对此我无能为力)。所以在新版本的包中,会包含
/opt/foo/etc/bar
这是一个文件。
如果我 运行 正常 rpm --upgrade pkg-2.0.rpm
,我什至在调用任何规范脚本之前就收到错误消息:
file /opt/foo/etc/bar from install of pkg-2.0-1.x86_64 conflicts with file from package pkg-1.0-1.x86_64
为了避免这种情况,我必须在我的 rpm
命令行中添加 --replacefiles
选项,这很糟糕。
即使我这样做了,它仍然失败了,这次是在我的 preinst scriptlet 运行s 之后,出现如下错误:
error: unpacking of archive failed on file /opt/foo/etc/bar: cpio: rename failed - Is a directory
error: pkg-2.0-1.x86_64: install failed
error: pkg-1.0-1.x86_64: erase skipped
据我所知,我能做到这一点的唯一方法是修改我的 preinst 以删除目录,并将 --replacefiles
选项添加到 rpm
。即使在我完成所有这些之后,虽然升级确实成功了,但它会为 "missing" (因为我删除了目录)的每个文件发出警告:
warning: file /opt/foo/etc/bar/x/y: remove failed: Not a directory
warning: file /opt/foo/etc/bar/z: remove failed: Not a directory
我不知道为什么会显示此错误,因为这些东西 不是 目录而且从来都不是,但无论如何。
我到处搜索关于这个特定问题的信息,虽然我发现了很多类似的错误,但它们都是针对不同情况的,例如人们试图安装两个文件重叠或类似的包.在这里,我肯定会尝试将一个版本的软件包升级到同一软件包的新版本。
似乎没有办法让这个在 RPM 中干净地工作;这只是 RPM 工具的缺陷还是我遗漏了什么?
这是rpm一直以来的突出问题。这是由CPIO引起的,它不能用文件替换目录(反之亦然)。
如果您不能更改路径名,那么您有两个选择 - 都是丑陋的技巧:
您从 A-1.0.rpm 开始,其中包括
/opt/foo/etc/bar/z
作为目录。然后你创建 A-transition-1.1.rpm 没有/opt/foo/etc/bar/z
目录(事实上 - 它可以是空包)并且你将Obsolete: A <= 0:1.0
。前导零是纪元。我假设你过去没有使用过它。然后您将创建新的 A-1.0.rpm 和Epoch: 1
并且您将Obsolete: A-transition < 0:2.0
并且这次它可以包含/opt/foo/etc/bar/z
作为文件。 RPM 将进行升级 0:A-1.0 -> A-transition -> 1:A-1.0因为这是一个 CPIO 问题,您可以:
%pre 如果 [ -d /opt/foo/etc/bar/z ];然后 rm -rf /opt/foo/etc/bar/z fi
RPM 会在删除旧包时大喊缺少 /opt/foo/etc/bar/z
,但它应该会通过(你没有测试过)。