当我尝试使用包含超过64000条记录的apache poi将数据写入excel表时,使用SXSSF并且我收到以下错误,
检测到拉链炸弹!该文件将超过最大值。压缩文件大小与扩展数据大小的比率。这可能表示该文件用于夸大内存使用量,因此可能带来安全风险。如果需要处理超出此限制的文件,可以通过ZipSecureFile.setMinInflateRatio()调整此限制。计数器:820224,cis.counter:8192,比率:0.009987515605493134Limits:MIN_INFLATE_RATIO:0.01
我找到了一个解决方案,通过添加ZipSecureFile.setMinInflateRatio(0.009)来说明,我需要知道它为什么会发生以及我需要为上述错误广告提供的限制在哪里添加解决方案,解决方案的参考: (How to determine if a Zip Bomb error thrown when retrieving an Excel files Styles Table is legitimate?)
如果有任何其他解决方案,请告知我们
答案 0 :(得分:7)
"拉链炸弹"是一个用于攻击向量的术语,其中小型zip文件扩展为非常大的未压缩文件,因此可能导致耗尽内存或磁盘空间等问题。
通常会创建此类拉链,目的是在从外部源接收zip文件的系统上导致拒绝服务攻击。
由于.xlsx文件实际上是包含XML文件的压缩文件,因此有可能在POI中造成这样的zip炸弹漏洞。
为了防止这种情况发生,Apache POI默认内置并启用了一些安全措施。因此,如果您创建包含不寻常内容的文件,例如许多行/列具有相同的内容,您可以遇到这些安全措施并接收异常,如上所示。
如果您完全控制已处理文件的创建,则可以调整错误消息中给出的设置以避免异常。
有关相关问题,请参阅https://bz.apache.org/bugzilla/show_bug.cgi?id=58499;有关类似讨论,请参见ZIp-bomb exception while writing a large formatted Excel (.xlsx)和How to determine if a Zip Bomb error thrown when retrieving an Excel files Styles Table is legitimate?。
答案 1 :(得分:6)
解决方法是在打开工作簿之前添加此行:
ZipSecureFile.setMinInflateRatio(0);
答案 2 :(得分:0)
您可以避免从InputStream读取zip炸弹问题而不是像这样读取文件
File fp = new File(excelFile);
FileInputStream fpis = new FileInputStream(fp);
try {
wb = WorkbookFactory.create(fpis);
} finally {
fpis.close();
}
但请注意WorkbookFactory.create(java.io.InputStream)处的文档说“从InputStream加载比从文件加载需要更多内存”