我正在尝试使用Jersey生成XSSFWorkbook。
我已经尝试了以下标题,似乎没有任何工作:
@Produces( “应用程序/ XML”)
@Produces( “应用程序/ vnd.openxmlformats-officedocument.spreadsheetml.sheet”)
@Produces( “应用程序/ vnd.openxml”
所有返回以下错误:
由com.sun.jersey.api.MessageException引发:Java类org.apache.poi.xssf.usermodel.XSSFWorkbook和Javatypesorg.apache.poi.xssf.usermodel.XSSFWorkbook和MIME的消息正文编写器媒体types的应用程序/ XML没有被发现… 37更多
基本上我有一个创buildXSSFWorkbook的函数,我想写出来供用户下载。 我能够做到这一点:
/* HttpServletResponse response; XssfWorkbook excel.write(response.getOutputStream()); */ @GET @Path("/excel/") @Produces("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet") public XSSFWorkbook exportReadingsAsExcel(@Context HttpServletResponse webResponse) { XSSFWorkbook excel = createExcel(); setHeader(webResponse, "export.xlsx"); try { excel.write(webResponse.getOutputStream()); } catch (IOException e) { e.printStackTrace(); } return excel; //ERROR IS HERE }
但是我也需要函数返回XSSFWorkbook出于其他原因。 我希望不要使用我可以让Jersey写出来的Web响应。
感谢您的帮助。
(我对Jersey和XSSF有点新鲜,如果因为我的术语或理解,请耐心等待)
您需要为XSSFWorkbook编写自定义编写器(或者找到一个编辑器)并将其插入泽西岛,如下所示:
@Provider @Produces("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet") public class CustomXSSFWorkbookWriter implements MessageBodyWriter { //This methode is the most important for you @Override public void writeTo(Object target, Class type, Type genericType, Annotation[] annotations, MediaType mediaType, MultivaluedMap httpHeaders, OutputStream outputStream) throws IOException {
然后你必须把这个类的包添加到你的web.xml
像这样:
<servlet> <servlet-name>Jersey REST Service</servlet-name> <servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class> <init-param> <param-name>com.sun.jersey.config.property.packages</param-name> <param-value>com.packages.to.your.views;com.packages.to.your.providers</param-value> </init-param>
泽西会让你自己的作家制作这个特定的格式。 对不起,我对XSSFWorkbook一无所知。
希望能解决你的问题。
我通过返回泽西岛的StreamingOutput解决了这个问题。 然后我将StreamingOutput的字节写出到OutputStream中。 我从OutputStream获得了byte [],将OutputStream写入InputStream,然后从该InputStream创建一个新的XSSFWorkbook。 我知道这是一个非常肮脏的做法。 我会尝试上面的-amille R建议的方式,希望能成为一个更清洁的解决方案。 但在此期间
@GET @Path("/excel/") @Produces("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet") public StreamingOutput exportReadingsAsExcel(@Context HttpServletResponse webResponse) { XSSFWorkbook excel = createExcel(); setHeader(webResponse, "export.xlsx"); StreamingOutput streamOutput = new StreamingOutput(){ public void write(OutputStream output) throws IOException, WebApplicationException { try { excel.write(output); } catch (Exception e) { throw new WebApplicationException(e); } } }; return streamOutput; }
在接收器功能上:
private XSSFWorkbook createExcel(StreamingOutput mStream){ XSSFWorkbook excel = new XSSFWorkbook(); try { ExcelOutputStream out = new ExcelOutputStream(); excel.write(out); ByteArrayInputStream inputStream = new ByteArrayInputStream(out.getBytes()); excel = new XSSFWorkbook(inputStream ; } catch (WebApplicationException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } return result; } class MyOutputStream extends OutputStream { private ByteArrayOutputStream myByteArray; public MyOutputStream(){ myByteArray = new ByteArrayOutputStream(); } @Override public void write(int b) throws IOException { // TODO Auto-generated method stub myByteArray.write(b); } public byte[] getBytes(){ return myByteArray.toByteArray(); } }