接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())

作者:慢时光\
来源:cnblogs.com/Tom-shushu/p/14279357.html
一、序言 Excel、PDF的导出、导入是我们工作中经常遇到的一个问题,刚好今天公司业务遇到了这个问题,顺便记个笔记以防下次遇到相同的问题而束手无策。
公司有这么两个需求:
需求一、给了一个表单,让把查出来的数据组装到表单中并且提供以PDF格式的下载功能。
需求二、 将数据查出来以Excel表格的形式下载下来。
二、Java实现PDF的生成和数据动态插入、导出功能 1、第一步:PDF制作模板
因为PDF常用的软件不让支持编辑,我们就先使用WPS以Word的形式进行编辑制作出与客户需求一样的样式,然后直接另存为 .pdf 的形式如下图所示:
a.Word里面制作模板
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

【接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())】b.更改名字为 .pdf形式
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

c.这时需要用到一个叫:Adobe Acrobat DC的软件,具体操作如下:
用Adobe Acrobat DC打开我们刚才改过名字的PDF文件,点击右下角的“更多工具”按钮
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

到下面这个页面再点击“准备表单”按钮
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

d.接下来就需要详细的配置你的数据源了
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

数据源即:你代码中实体类中对应的数据(注意字段一定要一一对应),配置完毕就可以保存进行下面的代码编写工作了。
2、代码的编写
假定我们实体类什么的都已经编写完成、数据通过前端传入获取、模板位置在E盘根目录下名字为:车辆维修审批单.pdf
导入jar包:

com.itextpdf itextpdf 5.5.13

实现生成PDF、数据插入、导出
@RegisterToSMP(serviceDisplay = "预览页面PDF下载") @RequestMapping(value = "https://www.it610.com/DM/gwclwxsq/qygl/exportPDF$m=query.service",method =RequestMethod.POST) public String exportPdf(@RequestBody GwclwxsqBean gwclwxsqBean , HttpServletResponse response) throws UnsupportedEncodingException { // 1.指定解析器 System.setProperty("javax.xml.parsers.DocumentBuilderFactory", "com.sun.org.apache.xerces.internal.jaxp.DocumentBuilderFactoryImpl"); String filename="车辆维修审批单.pdf"; String path="e:/"; response.setContentType("application/pdf"); response.setHeader("Content-Disposition", "attachment; fileName=" + URLEncoder.encode(filename, "UTF-8")); OutputStream os = null; PdfStamper ps = null; PdfReader reader = null; try { os = response.getOutputStream(); // 2 读入pdf表单 reader = new PdfReader(path+ "/"+filename); // 3 根据表单生成一个新的pdf ps = new PdfStamper(reader, os); // 4 获取pdf表单 AcroFields form = ps.getAcroFields(); // 5给表单添加中文字体 这里采用系统字体。不设置的话,中文可能无法显示 BaseFont bf = BaseFont.createFont("C:/WINDOWS/Fonts/SIMSUN.TTC,1", BaseFont.IDENTITY_H, BaseFont.EMBEDDED); form.addSubstitutionFont(bf); // 6查询数据================================================ Map data = https://www.it610.com/article/new HashMap(); data.put("commitTime", gwclwxsqBean.getCommitTime()); data.put("driver", gwclwxsqBean.getDriver()); data.put("carId", gwclwxsqBean.getCarId()); data.put("carType", gwclwxsqBean.getCarType()); data.put("repairAddress", gwclwxsqBean.getRepairAddress()); data.put("repairCost",gwclwxsqBean.getRepairCost()); data.put("project", gwclwxsqBean.getProject()); data.put("fwbzzxfzrYj", gwclwxsqBean.getFwbzzxfzrYj()); data.put("fgldspYj", gwclwxsqBean.getFgldspYj()); data.put("remarks", gwclwxsqBean.getRemarks()); // 7遍历data 给pdf表单表格赋值 for (String key : data.keySet()) { form.setField(key,data.get(key).toString()); } ps.setFormFlattening(true); log.info("*******************PDF导出成功***********************"); } catch (Exception e) {log.error("*******************PDF导出失败***********************"); e.printStackTrace(); } finally { try { ps.close(); reader.close(); os.close(); } catch (Exception e) { e.printStackTrace(); } } return null; }

3、测试
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

三、Java实现Excel生成和数据插入、导出 这个比较简单,直接上代码(假定你的实体类、查询什么的都已经写好)注意:实体类一个是你自己的数据实体类还有一个是你导出时表格中对应的实体类。100道Java中高级面试题汇总
我们以一个真实的公司业务来举个例子(一个统计疫情登记人员信息的Excel导出功能)
a.表头对应实体类ExportYqfkdj.java
import lombok.Data; /** * description: * @author: zhouhong * @version: V1.0.0 * @date: 2021年1月14日 下午3:05:54 */ @Data public class ExportYqfkdj { /** * 序号 */ private Integer xuhao; /** * 姓名 */ private String xingming; /** * 证件号码 */ private String zjhm; /** * 联系电话 */ private String lxdh; /** * 申请人工作单位 */ private String sqrGzdw; /** * 是否接触过疑似病例 */ private String sfjcgysbl; /** * 当前是否与居家隔离人员同住 */ private String sfyjjglrytz; /** * 当前状态 */ private String dqzt; /** * 当前健康状态 */ private String dqjkzt; /** * 当前体温 */ private String dqtw; /** * 当前所在地址 */ private String dqszdz; /** * 当前居住地址 */ private String dqjzdz; /** * 提交时间 * */ private String tjsj; }

b.Service层
/** * 导出 * @param yqfkdjBean * @author zhouhong * @return * @throws Exception */ @Transactional(rollbackFor = { Exception.class }) public DataResult exporYqfkdj(YqfkdjBean yqfkdjBean) throws Exception { DataResult result = new DataResult(); List list = new ArrayList(); try { /* 查询导出信息 */ result = getYqfkMhCXQuery(yqfkdjBean); SimpleDateFormat df = new SimpleDateFormat("yyyyMMddhhmmssSSS"); for (int i = 0; i < result.getTotalcount(); i++) { ExportYqfkdj dmKhfwdcDtjlZxDto = new ExportYqfkdj(); dmKhfwdcDtjlZxDto = ObjectUtil.parsePojo(result.getResults().get(i), ExportYqfkdj.class); dmKhfwdcDtjlZxDto.setXuhao(i + 1); list.add(dmKhfwdcDtjlZxDto); } String filepath = "D:/疫情防控信息" + df.format(new Date()) + ".xlsx"; if (System.getProperty(YqfkdjUtils.Wjdz.NAME).toLowerCase().startsWith(YqfkdjUtils.Wjdz.LI) || System.getProperty(YqfkdjUtils.Wjdz.NAME).toLowerCase().startsWith(YqfkdjUtils.Wjdz.LIN)) { filepath = "/home/Tomcat/temp/" + df.format(new Date()) + ".xlsx"; } EasyExcel.write(filepath, ExportYqfkdj.class).head(head()).sheet().doWrite(list); result.setResults(list); result.setSuccess(true); result.setMsg(filepath); } catch (Exception e) { result.setSuccess(false); result.setMsg(YqfkdjUtils.Cytx.DCSB); e.printStackTrace(); throw e; } return result; } /** * 疫情防控信息导出表头 * @author zhouhong * @return List */ private List head() { List list = new ArrayList(); List head0 = new ArrayList(); head0.add("序号"); List head1 = new ArrayList(); head1.add("姓名"); List head2 = new ArrayList(); head2.add("证件号码"); List head3 = new ArrayList(); head3.add("联系电话"); List head4 = new ArrayList(); head4.add("工作所在单位"); List head5 = new ArrayList(); head5.add("是否接触疑似病例"); List head6 = new ArrayList(); head6.add("是否与隔离人员同住"); List head7 = new ArrayList(); head7.add("当前状态"); List head8 = new ArrayList(); head8.add("当前健康状态"); List head9 = new ArrayList(); head9.add("体温(°C)"); List head10 = new ArrayList(); head10.add("当前所在地址"); List head11 = new ArrayList(); head11.add("当前居住地址"); List head12 = new ArrayList(); head12.add("提交时间"); list.add(head0); list.add(head1); list.add(head2); list.add(head3); list.add(head4); list.add(head5); list.add(head6); list.add(head7); list.add(head8); list.add(head9); list.add(head10); list.add(head11); list.add(head12); return list; }

c.Controller层
@RegisterToSMP(serviceDisplay = "疫情防控查询导出") @RequestMapping(value = "https://www.it610.com/DM/yqfkdj/gr/yqfkdjdc$m=export.service", method = RequestMethod.POST) public void exportKhfxxx(@RequestBody YqfkdjBean yqfkdjBean, HttpServletResponse resp) throws Exception { DataResult result = new DataResult(); try { SimpleDateFormat df = new SimpleDateFormat("yyyyMMddhhmmssSSS"); result = yqfkdjService.exporYqfkdj(yqfkdjBean); String filepath = result.getMsg().replace("\"", ""); File file = new File(filepath); String filename = "疫情防控信息" + df.format(new Date()) + ".xlsx"; InputStream fis = new BufferedInputStream(new FileInputStream(filepath)); byte[] buffer = new byte[fis.available()]; fis.read(buffer); fis.close(); resp.reset(); resp.setHeader("Content-Disposition", "attachment; filename=" + new String(filename.replaceAll(" ", "").getBytes("gbk"))); resp.setHeader("Content-Length", "" + file.length()); OutputStream os = new BufferedOutputStream(resp.getOutputStream()); resp.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"); // 输出文件 os.write(buffer); os.flush(); os.close(); } catch (Exception e) { e.printStackTrace(); log.info(YqfkdjUtils.Cytx.DCSB); throw e; } }

测试
接了个变态需求(生成 Excel + PDF 导出,用 Java 怎么实现())
文章图片

已经全部完成PDF和Excel的生成、插入、导出功能。
参考链接:https://www.cnblogs.com/wangp...
近期热文推荐:
1.1,000+ 道 Java面试题及答案整理(2021最新版)
2.别在再满屏的 if/ else 了,试试策略模式,真香!!
3.卧槽!Java 中的 xx ≠ null 是什么新语法?
4.Spring Boot 2.6 正式发布,一大波新特性。。
5.《Java开发手册(嵩山版)》最新发布,速速下载!
觉得不错,别忘了随手点赞+转发哦!

    推荐阅读