python - 如何读取包含在 gz 文件中的文件名

标签 python gzip compression

我尝试读取一个 gz 文件:

with open(os.path.join(storage_path,file), "rb") as gzipfile:
        with gzip.GzipFile(fileobj=gzipfile) as datafile:
            data = datafile.read()

它可以工作,但我需要包含在我的 gz 文件中的每个文件的文件名和大小。 此代码将包含文件的内容打印到存档中。

如何读取包含在这个 gz 文件中的文件名?

最佳答案

Python gzip 模块不提供对该信息的访问。

源代码跳过它而不存储它:

if flag & FNAME:
    # Read and discard a null-terminated string containing the filename
    while True:
        s = self.fileobj.read(1)
        if not s or s=='\000':
            break

文件名部分是可选的,不保证存在(命令行 gzip -c 解压缩选项将使用原始文件名 sans .gz 在这种情况下,我认为).未压缩的文件大小不存储在 header 中;您可以在最后四个字节中找到它。

要自己从文件头读取文件名,您需要重新创建文件头读取代码,并保留文件名字节。以下函数返回,加上解压缩后的大小:

import struct
from gzip import FEXTRA, FNAME

def read_gzip_info(gzipfile):
    gf = gzipfile.fileobj
    pos = gf.tell()

    # Read archive size
    gf.seek(-4, 2)
    size = struct.unpack('<I', gf.read())[0]

    gf.seek(0)
    magic = gf.read(2)
    if magic != '\037\213':
        raise IOError('Not a gzipped file')

    method, flag, mtime = struct.unpack("<BBIxx", gf.read(8))

    if not flag & FNAME:
        # Not stored in the header, use the filename sans .gz
        gf.seek(pos)
        fname = gzipfile.name
        if fname.endswith('.gz'):
            fname = fname[:-3]
        return fname, size

    if flag & FEXTRA:
        # Read & discard the extra field, if present
        gf.read(struct.unpack("<H", gf.read(2)))

    # Read a null-terminated string containing the filename
    fname = []
    while True:
        s = gf.read(1)
        if not s or s=='\000':
            break
        fname.append(s)

    gf.seek(pos)
    return ''.join(fname), size

将上述函数与已创建的 gzip.GzipFile 对象一起使用:

filename, size = read_gzip_info(gzipfileobj)

关于python - 如何读取包含在 gz 文件中的文件名,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15610587/

相关文章:

python - 将参数从批处理文件传递到 Python

python - 如果函数抛出异常则不返回是不好的做法吗?

linker - 在调试信息压缩标志的各种组合下,压缩的调试信息如何在汇编器和链接器之间流动?

javascript - 使用 KineticJS 绘制有根树

python - Sublime Text 解释器不支持 GUI

java - 为什么 gzip 压缩缓冲区大小大于未压缩缓冲区?

webpack - gzip 和 webpack 压缩

webserver - 服务器端 GZipping 如何工作?

compression - 在 Mac 中解压缩 .txt.gz 文件?

java - 如何读取 .zip 文件的前两个字节以确认是否存在适当的魔数(Magic Number)?