我正在寻找一种方法来更新数千个 .tbz 存档文件,因此我将使用 shell 脚本来完成此操作。我需要为每个文件添加一个文件。
我的问题是,是否有一种更快的方法来执行此操作,而无需提取每个 tbz 的内容,然后使用包含的 tar 中包含的新文件重新压缩?命令会是什么样子?
谢谢
答案1
虽然tar
可以将文件添加到已有的存档中,但无法对其进行压缩。您将不得不bunzip2
压缩存档,留下标准 tarball。然后,您可以使用tar
的功能将文件添加到现有存档,然后使用 重新压缩bzip2
。
从手册:
-r Like -c, but new entries are appended to the archive. Note that this only
works on uncompressed archives stored in regular files. The -f option is
required.
答案2
另一个答案是正确的:如果不解压缩压缩的 tar 存档,则无法正确更新它。GNU tar 文档提示它,并且尝试更新失败并显示明确的错误消息:
$ tar --concatenate --file=cat.tar.bz2 two.tar.bz2
tar: Cannot update compressed archives
tar: Error is not recoverable: exiting now
然而,如果您对不需要减压的肮脏的工作解决方案感兴趣,我可以根据以下观察提供一个:
- 支持使用附加 bzip2 流
cat
并生成有效的 bzip2 流(gzip 也是如此); - 使用附加 tars
cat
不会生成有效的 tar 文件,这就是该--concatenate
选项存在的原因,但我们可以要求 tar 假装它是有效的:
对于您来说,想要或尝试使用 cat 连接两个存档而不是使用该操作似乎更直观
--concatenate
;毕竟,cat 是组合文件的实用程序。然而,tar 存档包含一个文件结束标记,如果要将串联的存档作为一个存档正确读取,则必须将其删除。
--concatenate
在附加每个新存档之前,从目标存档中删除存档结束标记。如果使用 cat 合并存档,则结果将不是有效的 tar 格式存档。如果您需要从使用 cat 实用程序添加的存档中检索文件,请使用--ignore-zeros
(-i
) 选项。
基于这些知识,我们可以做,例如:
cat {one,two}.tar.bz2 >combined.tar.bz2
正如上面的文档片段所解释的,这会导致一个无效的 tar 文件,但使用--ignore-zeros
,仍然可以完全读取它:
## Show contents of `one.tar.bz2'
$ tar tf one.tar.bz2
a
b
## Show contents of `two.tar.bz2'
$ tar tf two.tar.bz2
c
## Show contents of `combined.tar.bz2', bypassing the bad format
$ tar tif combined.tar.bz2
a
b
c
请注意上面如何列出原始两个存档中的所有三个文件,而省略-i
(正确)仅列出第一个原始存档中的文件:
$ tar tf combined.tar.bz2
a
b
再说一次,这只不过是一个肮脏的把戏,但如果您控制写入和读取双方,并且可以确保-i
在尝试读取以这种方式创建的文件时使用它,它可能会很有用。