我创建了一个servlet,它创建了一个XSSFWorkbook并将其写入响应的outputStream。奇怪的是,当我尝试在浏览器中测试功能时(Chrome v54.0.2840.98),我只能获取一次xlsx文件(该文件打开时没有任何格式问题,并且还具有预期的内容)但是,如果我离开可以使用此功能的页面并使用' back'浏览器中的按钮并立即返回到同一页面并尝试再次获取相同的文件我没有在响应中获得任何内容。此外,我的其他servlet也停止工作,直到我打开一个新选项卡。我已经在不同的浏览器(Safari v9.1.2(11601.7.7))中试了一下,一切都按预期工作,没有任何问题。 这是我使用的代码:
@Override
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
DateTime now = new DateTime();
Workbook workbook = createWorkbook(); //creates an XSSFWorkbook
response.setContentType("application/vnd.ms-excel");
response.setHeader(
"Content-Disposition",
"attachment; filename=\"excel-export-" + now.toString("yyyy-MMM-dd") + ".xlsx\""
);
BufferedOutputStream bufferedOutputStream = new BufferedOutputStream(response.getOutputStream());
workbook.write(bufferedOutputStream);
}
当我在开发环境中运行代码时,我没有得到任何异常,状态为200,但仍然没有下载任何内容。偶尔我会得到一个
org.apache.poi.openxml4j.exceptions.OpenXML4JRuntimeException:Fail to save: an error occurs while saving the package : The part /docProps/core.xml fail to be saved in the stream with marshaller org.apache.poi.openxml4j.opc.internal.marshallers.ZipPackagePropertiesMarshaller
经过大量调试后,我可以通过将 null 传递给workbook.write()函数来重现:
workbook.write(null);
感谢任何帮助,感谢您的阅读!
Javax Servlet API v2.5 Apache-POI v3.15 Java 8 JDK(1.8.0_111)
更新 如果我得到一个异常,它看起来像这样(stacktrace): https://gist.githubusercontent.com/darkstar85/b151e53b64498e1fb476d0f6f8ea4eaf/raw/ffb078c54b850922fcd4e467a6ebf9695aeb7354/gistfile1.txt
答案 0 :(得分:1)
在查看Apache POI的代码时,只有在StreamHelper.saveXmlInStream(xmlDoc, out)
返回false
时才会发生这种情况。此外,如果XML转换在行trans.transform(xmlSource, outputTarget);
处失败,则仅返回false。
然而,它只是在这里进行身份转换(即简单复制),所以只有在应用程序中可用的XML Parser无法正常工作时才会失败。
因此,我会检查您使用的JDK以及您的应用程序中是否添加了任何其他XML解析器,例如: Xerces或任何其他,看看你是否可以删除它们。
答案 1 :(得分:-3)
我使用工作代码更新了您的功能。我的应用程序的唯一区别是我正在使用post resquest。你能试试吗?
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
DateTime now = new DateTime();
Workbook workbook = createWorkbook(); //creates an XSSFWorkbook
response.setContentType("application/vnd.ms-excel");
response.setHeader(
"Content-Disposition",
"attachment; filename=\"excel-export-" + now.toString("yyyy-MMM-dd") + ".xlsx\""
);
workbook.write(response.getOutputStream());
response.flushBuffer();
}