Python 中的 zipfile 生成不太正常的 ZIP 文件
zipfile in Python produces not quite normal ZIP files
在我的项目中,创建了一组文件并将其打包为 ZIP 存档,以便在 Android 移动设备 phone 上使用。 Android 应用程序正在打开此类 ZIP 文件以读取初始数据,然后将其工作结果存储到相同的 ZIP 中。我无法访问上述 Android 应用程序的源代码和之前生成 zip 文件的旧脚本(实际上,我不知道旧 ZIP 文件是如何创建的)。但是 ZIP 存档的结构是已知的,我已经编写了新的 python 脚本来制作相同的文件。
我遇到了以下问题:我的脚本生成的 ZIP 文件无法被 Android 应用程序打开(关于不正确的文件结构欠款的错误消息),但是如果我解压所有内容并将其打包回去通过 WinZIP、7-Zip 或“发送到 -> 压缩(zipped)文件夹”(在 Windows 7 中)文件通常在 phone 上处理(这使我得出结论,问题不在 Android 应用程序中)。
打包ZIP文件夹的代码片段如下
# make zip
try:
with zipfile.ZipFile(prefix + '.zip', 'w') as zipf:
for root, dirs, files in os.walk(prefix):
for file in files:
zipf.write(os.path.join(root, file))
# remove dir, that was packed
shutil.rmtree(prefix)
# Report about resulting
print('File ' + prefix + '.zip was created')
except:
print('Unexpected error occurred while creating file ' + prefix + '.zip')
在我注意到文件未压缩后,我添加了压缩选项:
zipfile.ZipFile(prefix + '.zip', 'w', zipfile.ZIP_DEFLATED)
但这并没有解决我的问题,为 allowZip64
设置 True
值也没有改变这种情况。
顺便说一下,使用 zipfile.ZIP_DEFLATED
生成的 ZIP 文件比 Windows 生成的 ZIP 文件小大约 5 KB,对于相同的存档内容,比 7-Zip 的结果小大约 14 KB。同时,我可以打开所有这些 ZIP 文件,以便通过 7-Zip 和 Windows Explorer 进行视觉比较。
所以我有三个相关的问题:
1) 是什么导致我的脚本在 zipfile
中出现这种奇怪的行为?
2) 我还能如何影响 zipfile
?
3) 如何检查用 zipfile
创建的 ZIP 文件以发现可能的结构问题或确保没有问题?
当然,如果我不得不放弃使用 zipfile
我可以使用外部压缩器(例如 7-zip)进行文件打包,但如果存在的话,我想找到一个优雅的解决方案。
更新:
为了检查用 zipfile
创建的 ZIP 文件的内容,我做了以下
# make zip
flist = []
try:
with zipfile.ZipFile(prefix + '.zip', 'w', zipfile.ZIP_DEFLATED) as zipf:
for root, dirs, files in os.walk(prefix):
for file in files:
zipf.write(os.path.join(root, file))
# Store item in the list
flist.append(os.path.join(root, file).replace("\","/"))
# remove dir, that was packed
shutil.rmtree(prefix)
# Report about resulting
print('File ' + prefix + '.zip was created')
except:
print('Unexpected error occurred while creating file ' + prefix + '.zip')
# Check of zip
with closing(zipfile.ZipFile(prefix + '.zip')) as zfile:
for info in zfile.infolist():
print(info.filename + \
' (extra = ' + str(info.extra) + \
'; compress_type = ' + ('ZIP_DEFLATED' if info.compress_type == zipfile.ZIP_DEFLATED else 'NOT ZIP_DEFLATED') + \
')')
# remove item from list
if info.filename in flist:
flist.remove(info.filename)
else:
print(info.filename + ' is unexpected item')
print('Number of items that were missed:')
print(len(flist))
并在输出中看到以下结果:
File en_US_00001.zip was created
en_US_00001/en_US_00001_0001/en_US_00001_0001_big.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_info.xml (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_small.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.pkl (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.tex (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_user.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_big.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_info.xml (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_small.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.pkl (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.tex (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_user.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_big.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_info.xml (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_small.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.pkl (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.tex (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_user.png (extra = b''; compress_type = ZIP_DEFLATED)
Number of items that were missed:
0
因此,所有内容都已写入,然后已读取,但问题仍然存在 - 是否已写入所有必要的内容?例如。哈罗德在评论中谈到了相对路径......也许,这是答案的关键
更新 2
当我使用外部 7-Zip 代码替换 zipfile
时
# make zip
subprocess.call(["7z.exe","a",prefix + ".zip", prefix])
shutil.rmtree(prefix)
# Check of zip
with closing(zipfile.ZipFile(prefix + '.zip')) as zfile:
for info in zfile.infolist():
print(info.filename)
print(' (extra = ' + str(info.extra) + '; compress_type = ' + str(info.compress_type) + ')')
print('Values for compress_type:')
print(str(zipfile.ZIP_DEFLATED) + ' = ZIP_DEFLATED')
print(str(zipfile.ZIP_STORED) + ' = ZIP_STORED')
产生以下结果
Creating archive en_US_00001.zip
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_big.png
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_info.xml
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_small.png
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_source.pkl
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_source.tex
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_user.png
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_big.png
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_info.xml
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_small.png
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_source.pkl
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_source.tex
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_user.png
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_big.png
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_info.xml
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_small.png
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_source.pkl
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_source.tex
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_user.png
Everything is Ok
en_US_00001/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00Faf\xd2Y\xf9\xd1\x01Faf\xd2Y\xf9\xd1\x01%\xc9c\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0001/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xbe(e\xd2Y\xf9\xd1\x01\xbe(e\xd2Y\xf9\xd1\x016\xf0c\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0001/en_US_00001_0001_big.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00G\x17d\xd2Y\xf9\xd1\x01G\x17d\xd2Y\xf9\xd1\x01G\x17d\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_info.xml
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00X>d\xd2Y\xf9\xd1\x01X>d\xd2Y\xf9\xd1\x01X>d\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_small.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00z\x8cd\xd2Y\xf9\xd1\x01ied\xd2Y\xf9\xd1\x01ied\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.pkl
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x8b\xb3d\xd2Y\xf9\xd1\x01\x8b\xb3d\xd2Y\xf9\xd1\x01\x8b\xb3d\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.tex
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xad\x01e\xd2Y\xf9\xd1\x01\xad\x01e\xd2Y\xf9\xd1\x01\xad\x01e\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_user.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xbe(e\xd2Y\xf9\xd1\x01\xbe(e\xd2Y\xf9\xd1\x01\xbe(e\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x005:f\xd2Y\xf9\xd1\x015:f\xd2Y\xf9\xd1\x01\xcfOe\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0002/en_US_00001_0002_big.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xe0ve\xd2Y\xf9\xd1\x01\xcfOe\xd2Y\xf9\xd1\x01\xcfOe\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_info.xml
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xf1\x9de\xd2Y\xf9\xd1\x01\xe0ve\xd2Y\xf9\xd1\x01\xe0ve\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_small.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x02\xc5e\xd2Y\xf9\xd1\x01\x02\xc5e\xd2Y\xf9\xd1\x01\x02\xc5e\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.pkl
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x13\xece\xd2Y\xf9\xd1\x01\x13\xece\xd2Y\xf9\xd1\x01\x13\xece\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.tex
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00$\x13f\xd2Y\xf9\xd1\x01$\x13f\xd2Y\xf9\xd1\x01$\x13f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_user.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x005:f\xd2Y\xf9\xd1\x015:f\xd2Y\xf9\xd1\x015:f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xdf\xc0g\xd2Y\xf9\xd1\x01\xdf\xc0g\xd2Y\xf9\xd1\x01Faf\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0003/en_US_00001_0003_big.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00W\x88f\xd2Y\xf9\xd1\x01W\x88f\xd2Y\xf9\xd1\x01W\x88f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_info.xml
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00h\xaff\xd2Y\xf9\xd1\x01h\xaff\xd2Y\xf9\xd1\x01h\xaff\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_small.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x9b$g\xd2Y\xf9\xd1\x01y\xd6f\xd2Y\xf9\xd1\x01y\xd6f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.pkl
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xacKg\xd2Y\xf9\xd1\x01\xacKg\xd2Y\xf9\xd1\x01\xacKg\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.tex
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xce\x99g\xd2Y\xf9\xd1\x01\xce\x99g\xd2Y\xf9\xd1\x01\xce\x99g\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_user.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xdf\xc0g\xd2Y\xf9\xd1\x01\xdf\xc0g\xd2Y\xf9\xd1\x01\xdf\xc0g\xd2Y\xf9\xd1\x01'; compress_type = 8)
Values for compress_type:
8 = ZIP_DEFLATED
0 = ZIP_STORED
据我了解,最重要的发现是:
- 包含文件夹信息的项目(例如
en_US_00001/
、en_US_00001/en_US_00001_0001/
),这些项目不在我使用 zipfile
生成的 ZIP 中
- 文件夹有
compress_type == ZIP_STORED
,而文件 compress_type == ZIP_DEFLATED
extra
s 有不同的值(生成了很长的字符串)
根据other question about zipfile的问题和示例的更新2中列出的差异,我尝试了以下代码将目录添加到ZIP文件并检查结果:
# make zip
try:
with zipfile.ZipFile(prefix + '.zip', 'w', zipfile.ZIP_DEFLATED) as zipf:
info = zipfile.ZipInfo(prefix+'\')
zipf.writestr(info, '')
for root, dirs, files in os.walk(prefix):
for d in dirs:
info = zipfile.ZipInfo(os.path.join(root, d)+'\')
zipf.writestr(info, '')
for file in files:
zipf.write(os.path.join(root, file))
# remove dir, that was packed
shutil.rmtree(prefix)
# Report about resulting
print('File ' + prefix + '.zip was created')
except:
print('Unexpected error occurred while creating file ' + prefix + '.zip')
# Check zip content
with closing(zipfile.ZipFile(prefix + '.zip')) as zfile:
for info in zfile.infolist():
print(info.filename)
print(' (extra = ' + str(info.extra) + '; compress_type = ' + str(info.compress_type) + ')')
print('Values for compress_type:')
print(str(zipfile.ZIP_DEFLATED) + ' = ZIP_DEFLATED')
print(str(zipfile.ZIP_STORED) + ' = ZIP_STORED')
输出为
File en_US_00001.zip was created
en_US_00001/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0001/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0002/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0003/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0001/en_US_00001_0001_big.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_info.xml
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_small.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.pkl
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.tex
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_user.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_big.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_info.xml
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_small.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.pkl
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.tex
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_user.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_big.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_info.xml
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_small.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.pkl
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.tex
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_user.png
(extra = b''; compress_type = 8)
Values for compress_type:
8 = ZIP_DEFLATED
0 = ZIP_STORED
向目录名称添加斜线(+'\'
或 +'/'
)似乎是强制性的。
最重要的是 - 现在 ZIP 文件已被 Android 应用程序正确接受。
在我的项目中,创建了一组文件并将其打包为 ZIP 存档,以便在 Android 移动设备 phone 上使用。 Android 应用程序正在打开此类 ZIP 文件以读取初始数据,然后将其工作结果存储到相同的 ZIP 中。我无法访问上述 Android 应用程序的源代码和之前生成 zip 文件的旧脚本(实际上,我不知道旧 ZIP 文件是如何创建的)。但是 ZIP 存档的结构是已知的,我已经编写了新的 python 脚本来制作相同的文件。
我遇到了以下问题:我的脚本生成的 ZIP 文件无法被 Android 应用程序打开(关于不正确的文件结构欠款的错误消息),但是如果我解压所有内容并将其打包回去通过 WinZIP、7-Zip 或“发送到 -> 压缩(zipped)文件夹”(在 Windows 7 中)文件通常在 phone 上处理(这使我得出结论,问题不在 Android 应用程序中)。
打包ZIP文件夹的代码片段如下
# make zip
try:
with zipfile.ZipFile(prefix + '.zip', 'w') as zipf:
for root, dirs, files in os.walk(prefix):
for file in files:
zipf.write(os.path.join(root, file))
# remove dir, that was packed
shutil.rmtree(prefix)
# Report about resulting
print('File ' + prefix + '.zip was created')
except:
print('Unexpected error occurred while creating file ' + prefix + '.zip')
在我注意到文件未压缩后,我添加了压缩选项:
zipfile.ZipFile(prefix + '.zip', 'w', zipfile.ZIP_DEFLATED)
但这并没有解决我的问题,为 allowZip64
设置 True
值也没有改变这种情况。
顺便说一下,使用 zipfile.ZIP_DEFLATED
生成的 ZIP 文件比 Windows 生成的 ZIP 文件小大约 5 KB,对于相同的存档内容,比 7-Zip 的结果小大约 14 KB。同时,我可以打开所有这些 ZIP 文件,以便通过 7-Zip 和 Windows Explorer 进行视觉比较。
所以我有三个相关的问题:
1) 是什么导致我的脚本在 zipfile
中出现这种奇怪的行为?
2) 我还能如何影响 zipfile
?
3) 如何检查用 zipfile
创建的 ZIP 文件以发现可能的结构问题或确保没有问题?
当然,如果我不得不放弃使用 zipfile
我可以使用外部压缩器(例如 7-zip)进行文件打包,但如果存在的话,我想找到一个优雅的解决方案。
更新:
为了检查用 zipfile
创建的 ZIP 文件的内容,我做了以下
# make zip
flist = []
try:
with zipfile.ZipFile(prefix + '.zip', 'w', zipfile.ZIP_DEFLATED) as zipf:
for root, dirs, files in os.walk(prefix):
for file in files:
zipf.write(os.path.join(root, file))
# Store item in the list
flist.append(os.path.join(root, file).replace("\","/"))
# remove dir, that was packed
shutil.rmtree(prefix)
# Report about resulting
print('File ' + prefix + '.zip was created')
except:
print('Unexpected error occurred while creating file ' + prefix + '.zip')
# Check of zip
with closing(zipfile.ZipFile(prefix + '.zip')) as zfile:
for info in zfile.infolist():
print(info.filename + \
' (extra = ' + str(info.extra) + \
'; compress_type = ' + ('ZIP_DEFLATED' if info.compress_type == zipfile.ZIP_DEFLATED else 'NOT ZIP_DEFLATED') + \
')')
# remove item from list
if info.filename in flist:
flist.remove(info.filename)
else:
print(info.filename + ' is unexpected item')
print('Number of items that were missed:')
print(len(flist))
并在输出中看到以下结果:
File en_US_00001.zip was created
en_US_00001/en_US_00001_0001/en_US_00001_0001_big.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_info.xml (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_small.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.pkl (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.tex (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0001/en_US_00001_0001_user.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_big.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_info.xml (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_small.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.pkl (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.tex (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0002/en_US_00001_0002_user.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_big.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_info.xml (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_small.png (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.pkl (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.tex (extra = b''; compress_type = ZIP_DEFLATED)
en_US_00001/en_US_00001_0003/en_US_00001_0003_user.png (extra = b''; compress_type = ZIP_DEFLATED)
Number of items that were missed:
0
因此,所有内容都已写入,然后已读取,但问题仍然存在 - 是否已写入所有必要的内容?例如。哈罗德在评论中谈到了相对路径......也许,这是答案的关键
更新 2
当我使用外部 7-Zip 代码替换 zipfile
时
# make zip
subprocess.call(["7z.exe","a",prefix + ".zip", prefix])
shutil.rmtree(prefix)
# Check of zip
with closing(zipfile.ZipFile(prefix + '.zip')) as zfile:
for info in zfile.infolist():
print(info.filename)
print(' (extra = ' + str(info.extra) + '; compress_type = ' + str(info.compress_type) + ')')
print('Values for compress_type:')
print(str(zipfile.ZIP_DEFLATED) + ' = ZIP_DEFLATED')
print(str(zipfile.ZIP_STORED) + ' = ZIP_STORED')
产生以下结果
Creating archive en_US_00001.zip
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_big.png
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_info.xml
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_small.png
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_source.pkl
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_source.tex
Compressing en_US_00001\en_US_00001_0001\en_US_00001_0001_user.png
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_big.png
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_info.xml
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_small.png
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_source.pkl
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_source.tex
Compressing en_US_00001\en_US_00001_0002\en_US_00001_0002_user.png
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_big.png
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_info.xml
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_small.png
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_source.pkl
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_source.tex
Compressing en_US_00001\en_US_00001_0003\en_US_00001_0003_user.png
Everything is Ok
en_US_00001/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00Faf\xd2Y\xf9\xd1\x01Faf\xd2Y\xf9\xd1\x01%\xc9c\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0001/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xbe(e\xd2Y\xf9\xd1\x01\xbe(e\xd2Y\xf9\xd1\x016\xf0c\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0001/en_US_00001_0001_big.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00G\x17d\xd2Y\xf9\xd1\x01G\x17d\xd2Y\xf9\xd1\x01G\x17d\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_info.xml
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00X>d\xd2Y\xf9\xd1\x01X>d\xd2Y\xf9\xd1\x01X>d\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_small.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00z\x8cd\xd2Y\xf9\xd1\x01ied\xd2Y\xf9\xd1\x01ied\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.pkl
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x8b\xb3d\xd2Y\xf9\xd1\x01\x8b\xb3d\xd2Y\xf9\xd1\x01\x8b\xb3d\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.tex
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xad\x01e\xd2Y\xf9\xd1\x01\xad\x01e\xd2Y\xf9\xd1\x01\xad\x01e\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_user.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xbe(e\xd2Y\xf9\xd1\x01\xbe(e\xd2Y\xf9\xd1\x01\xbe(e\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x005:f\xd2Y\xf9\xd1\x015:f\xd2Y\xf9\xd1\x01\xcfOe\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0002/en_US_00001_0002_big.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xe0ve\xd2Y\xf9\xd1\x01\xcfOe\xd2Y\xf9\xd1\x01\xcfOe\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_info.xml
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xf1\x9de\xd2Y\xf9\xd1\x01\xe0ve\xd2Y\xf9\xd1\x01\xe0ve\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_small.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x02\xc5e\xd2Y\xf9\xd1\x01\x02\xc5e\xd2Y\xf9\xd1\x01\x02\xc5e\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.pkl
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x13\xece\xd2Y\xf9\xd1\x01\x13\xece\xd2Y\xf9\xd1\x01\x13\xece\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.tex
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00$\x13f\xd2Y\xf9\xd1\x01$\x13f\xd2Y\xf9\xd1\x01$\x13f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_user.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x005:f\xd2Y\xf9\xd1\x015:f\xd2Y\xf9\xd1\x015:f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xdf\xc0g\xd2Y\xf9\xd1\x01\xdf\xc0g\xd2Y\xf9\xd1\x01Faf\xd2Y\xf9\xd1\x01'; compress_type = 0)
en_US_00001/en_US_00001_0003/en_US_00001_0003_big.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00W\x88f\xd2Y\xf9\xd1\x01W\x88f\xd2Y\xf9\xd1\x01W\x88f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_info.xml
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00h\xaff\xd2Y\xf9\xd1\x01h\xaff\xd2Y\xf9\xd1\x01h\xaff\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_small.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\x9b$g\xd2Y\xf9\xd1\x01y\xd6f\xd2Y\xf9\xd1\x01y\xd6f\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.pkl
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xacKg\xd2Y\xf9\xd1\x01\xacKg\xd2Y\xf9\xd1\x01\xacKg\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.tex
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xce\x99g\xd2Y\xf9\xd1\x01\xce\x99g\xd2Y\xf9\xd1\x01\xce\x99g\xd2Y\xf9\xd1\x01'; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_user.png
(extra = b'\n\x00 \x00\x00\x00\x00\x00\x01\x00\x18\x00\xdf\xc0g\xd2Y\xf9\xd1\x01\xdf\xc0g\xd2Y\xf9\xd1\x01\xdf\xc0g\xd2Y\xf9\xd1\x01'; compress_type = 8)
Values for compress_type:
8 = ZIP_DEFLATED
0 = ZIP_STORED
据我了解,最重要的发现是:
- 包含文件夹信息的项目(例如
en_US_00001/
、en_US_00001/en_US_00001_0001/
),这些项目不在我使用zipfile
生成的 ZIP 中
- 文件夹有
compress_type == ZIP_STORED
,而文件compress_type == ZIP_DEFLATED
extra
s 有不同的值(生成了很长的字符串)
根据other question about zipfile的问题和示例的更新2中列出的差异,我尝试了以下代码将目录添加到ZIP文件并检查结果:
# make zip
try:
with zipfile.ZipFile(prefix + '.zip', 'w', zipfile.ZIP_DEFLATED) as zipf:
info = zipfile.ZipInfo(prefix+'\')
zipf.writestr(info, '')
for root, dirs, files in os.walk(prefix):
for d in dirs:
info = zipfile.ZipInfo(os.path.join(root, d)+'\')
zipf.writestr(info, '')
for file in files:
zipf.write(os.path.join(root, file))
# remove dir, that was packed
shutil.rmtree(prefix)
# Report about resulting
print('File ' + prefix + '.zip was created')
except:
print('Unexpected error occurred while creating file ' + prefix + '.zip')
# Check zip content
with closing(zipfile.ZipFile(prefix + '.zip')) as zfile:
for info in zfile.infolist():
print(info.filename)
print(' (extra = ' + str(info.extra) + '; compress_type = ' + str(info.compress_type) + ')')
print('Values for compress_type:')
print(str(zipfile.ZIP_DEFLATED) + ' = ZIP_DEFLATED')
print(str(zipfile.ZIP_STORED) + ' = ZIP_STORED')
输出为
File en_US_00001.zip was created
en_US_00001/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0001/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0002/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0003/
(extra = b''; compress_type = 0)
en_US_00001/en_US_00001_0001/en_US_00001_0001_big.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_info.xml
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_small.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.pkl
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_source.tex
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0001/en_US_00001_0001_user.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_big.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_info.xml
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_small.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.pkl
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_source.tex
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0002/en_US_00001_0002_user.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_big.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_info.xml
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_small.png
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.pkl
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_source.tex
(extra = b''; compress_type = 8)
en_US_00001/en_US_00001_0003/en_US_00001_0003_user.png
(extra = b''; compress_type = 8)
Values for compress_type:
8 = ZIP_DEFLATED
0 = ZIP_STORED
向目录名称添加斜线(+'\'
或 +'/'
)似乎是强制性的。
最重要的是 - 现在 ZIP 文件已被 Android 应用程序正确接受。