POI,全称Apache POI,是Apache软件基金会的开放源码函式库,POI提供API给Java程序对Microsoft Office格式档案读和写的功能。项目地址:Apache POI - the Java API for Microsoft Documents
1 导入
使用form表单(enctype="multipart/form-data")上传excel文件,后台接收MultipartFile文件格式。
读取excel
private static final String EXCEL_XLS = "xls"; private static final String EXCEL_XLSX = "xlsx"; /** * 判断Excel的版本,获取Workbook * @param in * @param file * @return * @throws IOException */ public static Workbook getWorkbok(InputStream in, MultipartFile file) throws IOException { Workbook wb = null; if(file.getOriginalFilename().endsWith(EXCEL_XLS)){ //Excel 2003 wb = new HSSFWorkbook(in); }else if(file.getOriginalFilename().endsWith(EXCEL_XLSX)){ // Excel 2007/2010 wb = new XSSFWorkbook(in); } return wb; } /** * 判断文件是否是excel * @throws Exception */ public static void checkExcelVaild(MultipartFile file) throws Exception{ if(ToolUtil.isEmpty(file)){ throw new Exception("文件不存在"); } if(!((file.getOriginalFilename().endsWith(EXCEL_XLS) || file.getOriginalFilename().endsWith(EXCEL_XLSX)))){ throw new Exception("文件不是Excel"); } } /** * 读取Excel,兼容 Excel 2003/2007/2010
* @param excelFile
* @param sheetIndex 从第几个sheet开始遍历
* @param dataRowIndex 从第几行开始遍历
* @throws Exception */ public static List
控制层
/** * 导入excel * * @param multipartFile * @return */ @RequestMapping(value = "/importExcel", method = RequestMethod.POST) @ResponseBody public void importExcel(@RequestParam("file") MultipartFile multipartFile) { if (multipartFile == null) { throw new Exception("excel文件请求参数错误"); } List> list = ExcelUtil.parseExcelObject(multipartFile, 0, 0); // 这里只解析第一个sheet,从第一行开始 for(Map map : list){ System.out.println(map.getString("name")); } }
1 导出
如果你想看到下载弹框提示,如下图,那么就需要使用form表单提交方式,请求后台接口。接下来会解释为什么。
写入excel
public static XSSFWorkbook createExcelObject(Listlist) { SimpleDateFormat fmt = new SimpleDateFormat("yyyy-MM-dd"); try { // 第一步,创建一个webbook文件,对应一个excel文件 XSSFWorkbook wb = new XSSFWorkbook(); // 第二部,在excel中添加一个sheet工作簿,参数为该工作簿名字,不写为默认; XSSFSheet sheet = wb.createSheet("sheet1"); // 第三部,做sheet中添加表头第0行,注意老版本poi对excel的行数列数有限制short XSSFRow row = sheet.createRow((int) 0); // 第四部,设置单元格样式 XSSFCellStyle style = wb.createCellStyle(); style.setAlignment(HorizontalAlignment.CENTER);//创建一个居中格式 // 生成字体 Font font = wb.createFont(); font.setFontHeightInPoints((short) 12); font.setBold(true); // 把字体应用到当前的样式 style.setFont(font); // 第五部,设置好表头内容 XSSFCell cell = row.createCell(0); cell.setCelSPUue("name"); cell.setCellStyle(style) // 第六部,写入实体数据 实际应用中这些数据应该是从数据库中得到 for (int i = 0; i < list.size(); i++) { // 每次新建一行然后在新行中插入list中的数据对象,有点繁琐,也许有更好的封装方法,留待后看 row = sheet.createRow((int) i + 1); row.createCell((int) 0).setCellValue(list.get(i).getName()); } return wb; } catch (Exception e) { e.printStackTrace(); } finally { } return null; }
控制层
/** * 导出商品信息 * * @param request * @param response * @throws Exception */ @RequestMapping(value = "/downExcel",method = RequestMethod.POST) @ResponseBody public void downExcel(HttpServletRequest request, HttpServletResponse response){ Listlist; // 查询出来的数据 // 正确代码顺序 //FileInputStream fs=new FileInputStream(excel); //XSSFWorkbook workbook = new XSSFWorkbook(fs); //FileOutputStream out=new FileOutputStream(excel); //workbook.write(out); XSSFWorkbook wb = ExcelUtil.createExcelObject(list); if (wb == null) throw new Exception("excel文件解析异常"); try { // 设置输出的格式 response.reset();// 清空输出流 response.setHeader("Content-Disposition", "attachment; filename=" + new String(("excel.xlsx").getBytes(), "iso-8859-1"));// 设定输出文件头 response.setContentType("application/x-download;charset=GBK");// 定义输出类型 //创建输出流 OutputStream outputStream = response.getOutputStream(); wb.write(outputStream); outputStream.close(); }catch (Exception e){ e.printStackTrace(); } }
3 疑难解答
1、为什么一定要form表单请求,才会出现下载弹框?而ajax请求方式却不会出现
因为,导出excel,在通过后台生成excel文件,并且以文件流的形式传递给前端,而ajax接收的返回数据类型只能是:字符串、xml。所以ajax处理不了返回的文件流。而浏览器可以处理。
2、注意,导出时的代码顺序,否则报错NotOfficeXmlFileException?
假如,你直接先把输入流,输出流建立好了以后,再创建新对象,就会报错。错误信息为: org.apache.poi.openxml4j.exceptions.NotOfficeXmlFileException: No valid entries or contents found, this is not a valid OOXML (Office Open XML) file。
导出->控制层代码,已经给出了正确的顺序。
欢迎大家评论与交流,加油!!
【参考】
- https://blog.csdn.net/phil_jing/article/details/78307819
- https://www.cnblogs.com/xbq8080/p/7344258.html ajax请求导出excel的问题
- https://blog.csdn.net/anlian523/article/details/72268347 XSSFWorkbook的顺序问题