有没有办法将 zip 转换为 tar 而不将其提取到文件系统?

有没有办法将 zip 转换为 tar 而不将其提取到文件系统?

有没有办法将zip存档转换为tar存档而无需先提取到临时目录? (并且没有编写我自己的taror实现unzip

答案1

现在可以从 PyPI 作为可安装命令使用,请参阅本文末尾。


我不知道有任何“标准”实用程序可以这样做,但是当我需要此功能时,我编写了以下 Python 脚本来从 ZIP 压缩到 Bzip2 压缩的 tar 存档,而无需先将任何内容提取到磁盘:

#! /usr/bin/env python
    
"""zip2tar """

import sys
import os
from zipfile import ZipFile
import tarfile
import time

def main(ifn, ofn):
    with ZipFile(ifn) as zipf:
        with tarfile.open(ofn, 'w:bz2') as tarf:
            for zip_info in zipf.infolist():
                #print zip_info.filename, zip_info.file_size
                tar_info = tarfile.TarInfo(name=zip_info.filename)
                tar_info.size = zip_info.file_size
                tar_info.mtime = time.mktime(tuple(zip_info.date_time) +
                                         (-1, -1, -1))
                tarf.addfile(
                    tarinfo=tar_info,
                    fileobj=zipf.open(zip_info.filename)
                )

input_file_name = sys.argv[1]
output_file_name = os.path.splitext(input_file_name)[0] + '.tar.bz2'

main(input_file_name, output_file_name)

只需将其保存到zip2tar并使其可执行,或者将其保存到zip2tar.py并运行python zip2tar.py。提供 ZIP 文件名作为脚本的参数,输出文件名将xyz.zipxyz.tar.bz2.

Bzip2 压缩输出通常比 zip 文件小得多,因为后者不对多个文件使用压缩模式,但如果 Bzip2 文件中出现错误,恢复后续文件的机会也较小。

如果您不希望压缩输出,请从代码中删除:bz2和。.bz2


如果你已经pip安装在python3环境中,你可以这样做:

pip3 install ruamel.zip2tar

获取zip2tar执行上述操作的命令行实用程序(免责声明:我是该包的作者)。

答案2

tar命令处理文件系统。它的输入是文件列表,然后从文件系统读取该列表(包括大量元数据)。您需要将 zip 文件呈现为文件系统,以便命令tar读取它。

虚拟文件系统 - AVFS将允许任何程序通过标准文件系统接口查看存档或压缩文件的内部保险丝

里面有一些详细的信息avfs-fuse 自述文件还有一些分布 为了它。

如果你安装了AVFS,那么你就可以

mountavfs
cd ~/.avfs/path/to/somefile.zip#
tar -cvf /path/whatever.tar .

AVFS 将填充 zip 中缺少的文件系统的任何信息,例如 tar 将拾取的文件所有权。

答案3

Linux 有一组很棒的工具,可以通过管道通过 stdin 和 stdout 进行工作。

unzip -p ./fzs-2015-03-18.zip | bzip2 > fzs-2015-03-18.bz

检查是否创建了临时文件

ps -ef | grep unzip
auser      44260    6666  3 11:18 pts/2    00:00:02 unzip -p ./fzs-2015-03-18.zip
auser      44434   44370  0 11:19 pts/1    00:00:00 grep --color=auto unzip


lsof -p 44260
COMMAND   PID  USER   FD   TYPE DEVICE  SIZE/OFF    NODE NAME
unzip   44260 auser  cwd    DIR  259,6      4096 3015712 /home/auser/Documents/shares/logs
unzip   44260 auser  rtd    DIR  259,5      4096       2 /
unzip   44260 auser  txt    REG  259,5    178072  680357 /usr/bin/unzip
unzip   44260 auser  mem    REG  259,5   3040368  744942 /usr/lib/locale/locale-archive
unzip   44260 auser  mem    REG  259,5   2146832  666811 /usr/lib/libc-2.31.so
unzip   44260 auser  mem    REG  259,5     74440  751069 /usr/lib/libbz2.so.1.0.8
unzip   44260 auser  mem    REG  259,5    203056  665072 /usr/lib/ld-2.31.so
unzip   44260 auser    0u   CHR  136,2       0t0       5 /dev/pts/2
unzip   44260 auser    1w  FIFO   0,13       0t0  436437 pipe
unzip   44260 auser    2u   CHR  136,2       0t0       5 /dev/pts/2
unzip   44260 auser    3r   REG  259,6 513348882 3015900 /home/auser/Documents/shares/logs/fzs-2015-03-18.zip



ps -ef | grep bzip2
auser      44262    6666 99 11:18 pts/2    00:06:42 bzip2
auser      45111   44370  0 11:25 pts/1    00:00:00 grep --color=auto bzip2

⟩ lsof -p 44262
COMMAND   PID  USER   FD   TYPE DEVICE SIZE/OFF    NODE NAME
bzip2   44262 auser  cwd    DIR  259,6     4096 3015712 /home/auser/Documents/shares/logs
bzip2   44262 auser  rtd    DIR  259,5     4096       2 /
bzip2   44262 auser  txt    REG  259,5    38744  655763 /usr/bin/bzip2
bzip2   44262 auser  mem    REG  259,5  2146832  666811 /usr/lib/libc-2.31.so
bzip2   44262 auser  mem    REG  259,5    74440  751069 /usr/lib/libbz2.so.1.0.8
bzip2   44262 auser  mem    REG  259,5   203056  665072 /usr/lib/ld-2.31.so
bzip2   44262 auser    0r  FIFO   0,13      0t0  436437 pipe
bzip2   44262 auser    1w   REG  259,6 97325056 3015902 /home/auser/Documents/shares/logs/fzs-2015-03-18.bz
bzip2   44262 auser    2u   CHR  136,2      0t0       5 /dev/pts/2

只要管子|436437 pipe

超级简单。

您可以替换bzip2gzip或其他一些通过 stdin 接受管道输入的实用程序

该 zip 文件包含数千个文本文件。

答案4

使用 libarchive 的bsdtar

bsdtar -zcf file.tar.gz @file.zip

来自手动的:

tar 创建并操作流归档文件。该实现可以从 tar、pax、cpio 中提取,压缩、jar、ar、xar、rpm、7-zip 和 ISO 9660 cdrom 映像,并可以创建柏油、pax、cpio、ar、zip、7-zip 和 shar 存档。

@archive
c仅限r模式)指定的存档将被打开,其中的条目将被追加到当前存档中。举个简单的例子,

tar -c -f - newfile @original.tar

将新存档写入标准输出,其中包含文件newfile 和 中的所有条目original.tar。相比之下,

tar -c -f - newfile original.tar

创建一个只有两个条目的新存档。相似地,

tar -czf - --format pax @-

从标准输入读取存档(其格式将自动确定)并将其转换为标准输出上的 gzip 压缩的 pax 格式存档。 这样,tar 就可以用来将档案从一种格式转换为另一种格式

相关内容