最近有一个需求,须要根据excel模板PDF报表;须要先根据excel模板生成excel文件,再由excel生成pdf文件,最后下载功;前端
使用
easypoi
组件,详细可参考文档中excel模板部分;linux
该方式的优点为样式与模板样式彻底一致,能够实现单值属性与列表遍历;ajax
easypoi
支持的表达式;TemplateParam
(模板属性)和数据属性;ExcelExportUtil.exportExcel
纯JAVA实现的PDF生成方法,跨平台,缺点也很明显:API比较难用,同时很难处理Excel的样式;后端
导入jar包: com.artofsolving-jodconverter浏览器
openOffice监听端口:soffice.exe -headless -accept="socket,host=%s,port=%s;urp;" -nofirststartwizard
服务器
//链接 var conn = new SocketOpenOfficeConnection(hostname,port); conn.connect(); //转换 converter = new OpenOfficeDocumentConverter(conn); converter.convert(docFile,pdfFile); //关闭链接 conn.disconnect();
优点: 跨平台;
缺点: openOffice转换成的PDF在必定程度失真,好比excel边框自动加粗等,某一些样式不支持等,可是linux服务器上的惟一选择.app
导入jar包: jacob-1.19.zipless
安装windowOffice或wps;前后端分离
//office命令 ActiveXComponent app = new ActiveXComponent("Excel.Application"); //Wps方式 app = new ActiveXComponent("KET.Application"); app.setProperty("Visible", false); Dispatch excels = app.getProperty("Workbooks").toDispatch(); excel = Dispatch.call(excels, "Open", path, false, true).toDispatch(); Dispatch.call(excel, "ExportAsFixedFormat", 0, pdfAbsPath);
优势: 完美的样式;
缺点: 仅支持window服务器;socket
response.setCharacterEncoding(CharsetUtil.UTF_8); response.setContentType("application/pdf"); response.setHeader("Content-Disposition","attachment; filename=" + fileName); response.setContentLengthLong(pdfFile.length());
config.responseType = "blob"; let blob = new Blob([response.data],{type: 'application/pdf'}); //建立一个blob对象 let downloadName = response.headers["content-disposition"].split(";")[1].split("filename=")[1]; let a = document.createElement('a'); let url = URL.createObjectURL(blob) a.href = url; // response is a blob a.download = downloadName; //文件名称 a.style.display = 'none'; document.body.appendChild(a); a.click(); a.remove();
缺点: 在safari中出现下载文件名为:known的异常;
该方法是上一种方法的扩展,不本身建立a标签,使用file-sever组件,只须要传入blob对象便可;
FileSaver.saveAs(blob, downloadName);
缺点: 在safari中出现下载文件名为:known的异常;
let a = document.createElement('a'); a.href = url; // 直接为后端的url; a.style.display = 'none'; document.body.appendChild(a); a.click(); a.remove();
优势:理论上全部浏览器都可正确识别文件名信息; 缺点: 由于不是经过ajax请求的后端接口,在先后端分离系统中要单独处理权限验证的东西(如token等);