我使用StringIO
和zipfile
创建了一个内存中的zip文件:
inMemoryZip = StringIO()
outfile = zipfile.ZipFile(inMemoryZip, 'w', compression=zipfile.ZIP_DEFLATED)
//outfile.write(stuff)
inMemoryZip.seek(0)
return inMemoryZip
此数据上传到服务器/数据库。在某些时候,它被检索,我需要将其作为zip文件写入磁盘。我不知道该怎么做。我尝试了以下方法:
with open('pathToNewZip.zip', 'w') as archive:
archive.write(inMemoryZip.getvalue())
这会创建zip文件存档,但是当我双击它时,我看不到它的内容,它基本上会创建一个自身的副本(另一个相同的.zip文件, ,但扩展名是。 zip.cpgz )旁边的原始
我也尝试过:
with open('pathToNewZip.zip', 'w') as archive:
shutil.copyfileobj(inMemoryZip, archive)
但与上述结果相同。
我猜部分问题是我不知道如何解析这些数据。 inMemoryZip
(StringIO
的实例)可能包含多个文件。
每个文件都写成新行吗?
.getvalue()
返回什么? StringIO
实例中所有文件的数据?
如何确定我之前压缩的文件的名称,以便可以使用相同的名称重新创建它们?
有这样的:How can I pass a Python StringIO() object to a ZipFile(), or is it not supported?但看起来如果一次只写入1个文件就行了。我的StringIO
实例可以包含1个文件或10个文件。
答案 0 :(得分:2)
您需要按照@Kupiakos的建议打开最终文件“wb”,否则最终会导致存档损坏。您的另一个问题是在使用StringIO
缓冲区之前需要关闭zip文件。 close将文件目录写入zipfile。如果没有这个,一个解压缩器可能会做出这样的假设,例如这只是多部件拉链中的一个并做奇怪的事情。名义上,只需添加outfile.close()
或将其放入上下文管理器
inMemoryZip = StringIO()
with zipfile.ZipFile(inMemoryZip, 'w', compression=zipfile.ZIP_DEFLATED) as output:
//outfile.write(stuff)
inMemoryZip.seek(0)
return inMemoryZip
然后再
with open('pathToNewZip.zip', 'wb') as archive:
archive.write(inMemoryZip.getvalue())