我们的团队有一个程序可以生成用Java编写的PDF。 PDF可能具有非ASCII文件名,使用Apache Commons Compress进行压缩。然后将zip文件上载到S3以供Windows和Mac客户端下载。
使用本机工具在Mac上解压缩时,会使用正确的文件名重新创建文件。但是,尝试使用本机Windows UI工具解压缩时,文件名创建不正确。
拉链过程是:
import org.apache.commons.compress.archivers.zip.ZipArchiveEntry;
我添加了以下代码,它仍无效,在Windows上显示不可读的字符:
zipFile.setEncoding("UTF-8");
zipFile.setUseLanguageEncodingFlag(true);
zipFile.setCreateUnicodeExtraFields(ZipArchiveOutputStream.UnicodeExtraFieldPolicy.ALWAYS);
如何创建可供Mac和Windows使用的zip文件?
答案 0 :(得分:2)
根据Apache Commons Compress页面:(https://commons.apache.org/proper/commons-compress/zip.html)
Windows“压缩文件夹”功能无法识别任何标记或额外字段,并使用平台默认编码创建存档 - 并且在阅读时希望存档采用该编码。
和
如果Windows“压缩文件夹”是您的主要消费者,那么您最好的选择是将编码显式设置为目标平台。您可能希望启用Unicode额外字段的创建,以便支持它们的工具将正确提取文件名。
因此:
如果您知道您的Windows用户位于地球的有限区域且您的文件名仅限于该区域(例如所有拉丁语),您可以留意Apache的建议并为文件名编码定义一个8位代码页, OS X的解压缩得到尊重。但是,这意味着它不适用于不同地区的Windows机器或意外使用略有不同的代码页(北美与西欧)。
明智的替代方案是在Windows上使用备用存档工具,并可能使用其他存档格式。也许您可以通过在zip文件中添加合适的提取工具来为Windows创建自解压存档。例如,您可以使用以下粗略说明在Java中创建自解压7zip存档:http://sourceforge.net/p/sevenzip/discussion/45798/thread/de8aa3c6
伪格式是:
7z.sfx + config.txt + your-created-archive.7z your-created-archive.exe
7z.sfx
是7zip分发的7zip自解压可执行文件“header”。
回应有问题的评论:
Windows使用UTF-16作为文件名,AFAIK在其调用的低级API中使用UTF-16。但是,Windows控制台非常破碎,并且不能快速支持UTF-8。
(Java还在内部对String对象使用UTF-16)
OS X对文件名编码强制执行UTF-8,因此Java在创建文件名时也应该尊重它。