将文件添加到tbz文件


8

我正在寻找一种更新数千个.tbz存档文件的方法,因此我将使用Shell脚本进行此操作。我需要向每个文件添加一个文件。

我的问题是,有没有一种更快的方法,而无需提取每个tbz的内容,然后使用包含的tar中包含的新文件进行重新压缩?这些命令是什么样的?

谢谢


一个明显的替代方案是将压缩文件放入未压缩的tarball中。但这改变了数据格式,因此对于您而言可能不可行,并且对于大量带有冗余的小文件而言,效率可能很低。
恢复莫妮卡

Answers:


12

虽然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.

确实如此
Kiwy

这是一种方法,但不是唯一的方法。可以在不完全解压缩bzip2流的情况下对其进行修改。我不知道是否有可能以允许将其干净地附加到tar存档中的方式来实现,但是dhag显示了部分方法。
吉尔(Gilles)'所以

10

另一个答案是正确的:如果不解压缩tar存档,就无法正确更新它。GNU tar文档对此进行了提示,并且尝试更新失败并显示了明确的错误消息:

$ tar --concatenate --file=cat.tar.bz2 two.tar.bz2 
tar: Cannot update compressed archives
tar: Error is not recoverable: exiting now

但是,如果您对不需要减压的肮脏的工作方式解决方案感兴趣,我可以根据以下发现提供一种解决方案:

  • cat支持使用附加bzip2流,并生成有效的bzip2流(gzip也是如此);
  • 使用追加cattar不会产生有效的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在尝试从以这种方式创建的文件中进行读取时可以使用该方法,那么它可能会很有用。


非常感谢您的详细回复。不幸的是,我无法控制最终读取这些档案的过程。
BottleZero

这可以用来“隐藏”档案中的某些文件,以便随便提取文件的人只会得到原始tarball的内容,但是那些知道将其添加i到命令行的人将看到整个内容。
Monty Harder '18
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.