繁体   English   中英

Python管道到`gzip.open`文件句柄

[英]Python piping to `gzip.open` filehandle

以下代码段将打开一个gzip文件句柄并向其中写入一行,然后以附加模式再次打开它,并将子进程的stdout重定向到gzip压缩的文件句柄。

import gzip
import subprocess

with gzip.open("./file.txt.gz", "w") as fh:
    fh.write("this is the first line\n")

with gzip.open("./file.txt.gz", "a") as fh:
    subprocess.call("echo this is the second line", shell=True, stdout=fh)

当我尝试将文件解压缩以查看写入的内容时,出现以下错误

$ gunzip file.txt.gz
gzip: file.txt.gz: decompression OK, trailing garbage ignored

解压缩的内容仅包含第一行

$ cat file.txt
this is the first line

当我使用相同的文件句柄编写行并作为流程的输出时,我得到的文件甚至未被gunzip识别。

import gzip
import subprocess

with gzip.open("./file.txt.gz", "w") as fh:
    fh.write("this is the first line\n")
    subprocess.call("echo this is the second line", shell=True, stdout=fh)

例如,生成的文件不能是gunzip

$ gunzip file.txt.gz

gzip: file.txt.gz: not in gzip format

是否可以通过subprocess进程将gzip风格的伪文件句柄传递给进程运行,或者真的没有其他方法可以写未压缩的文件然后返回并对其进行压缩?

如果您搜索StackOverflow,您会发现偶尔会出现此问题,但是答案并非总是易于实现的。 它们的要旨似乎是subprocess.call()无法传递伪文件句柄-它必须是真实的东西。 标准的解决方法似乎是使用subprocess.Popen()

但是,这是我解决的一个简单折衷方案:

import gzip
import subprocess

with gzip.open("file.txt.gz", "wt") as handle:
    handle.write("this is the first line\n")

completed = subprocess.run("echo 'this is the second line'", shell=True, stdout=subprocess.PIPE, universal_newlines=True)

with gzip.open("file.txt.gz", "at") as handle:
    handle.write(completed.stdout)

这个想法是将压缩数据的添加延迟到子流程完成之后:

> gzcat file.txt.gz
this is the first line
this is the second line
> 

在Python 3.5中添加了subprocess.run()函数

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM