这里用了POI组件,需要引入的jar包有:
curvesapi-1.03.jar
poi-3.14-20160307.jar
poi-ooxml-3.14-20160307.jar
poi-ooxml-schemas-3.14-20160307.jar
xmlbeans-2.6.0.jar
参考: POI组件:POI操作Excel |
1、用户列表导出成Excel
1.1、listUI.jsp
UI部分
<input type="button" value="导出" class="s_button" onclick="doExportExcel()"/> <input name="userExcel" type="file"/> <input type="button" value="导入" class="s_button" onclick="doImportExcel()"/>
Javascript部分
//导出用户列表 function doExportExcel(){ window.open("${basePath}/tax/user_exportExcel.action"); } //导入 function doImportExcel(){ document.forms[0].action = "${basePath}/tax/user_importExcel.action"; document.forms[0].submit(); }
1.2、UserAction.java
//导出用户列表 public void exportExcel() { try { //1、查找用户列表 userList = userService.findAll(); //2、导出 HttpServletRequest request = ServletActionContext.getRequest(); String userAgent = request.getHeader("user-agent"); System.out.println(userAgent); HttpServletResponse response = ServletActionContext.getResponse(); response.setContentType("application/octet-stream"); response.setHeader("Content-Disposition", "attachment;filename=" + new String("用户列表.xls".getBytes(),"ISO-8859-1")); ServletOutputStream outputStream = response.getOutputStream(); userService.exportExcel(userList,outputStream); if(outputStream != null){ outputStream.close(); } } catch (Exception e) { e.printStackTrace(); } }
知识点(1) new String("用户列表.xls".getBytes(),"ISO-8859-1")
关于这一点,它的目的是解决中文乱码的问题。 我查了一些资料,也进行了测试(包括Chrome、Firefox、IE11),new String("用户列表.xls".getBytes(),"ISO-8859-1")能正常显示中文。 在做文件下载时,当文件名为中文时,经常会出现乱码现象。 大体的原因就是header中只支持ASCII,所以我们传输的文件名必须是ASCII,当文件名为中文时,必须要将该中文转换成ASCII。 这里说的ASCII码和ISO-8859-1的关系是什么 ASCII码的取值范围是0~127,可以用7个bit表示。 绝大多数计算机的一个字节是8位,取值范围是0~255,而ASCII码并没有规定编号为128~255的字符,为了能表示更多字符,各厂商制定了很多种ASCII码的扩展规范。注意,虽然通常把这些规范称为扩展ASCII码(Extended ASCII),但其实它们并不属于ASCII码标准。 在图形界面中最广泛使用的扩展ASCII码是ISO-8859-1,也称为Latin-1,其中包含欧洲各国语言中最常用的非英文字母,但毕竟只有128个字符,某些语言中的某些字母没有包含。 转换方式有很多: 方式一:将中文文件名用ISO-8859-1进行重新编码,如headers.add("Content-disposition","attachment;filename="+new String("中国".getBytes("UTF-8"),"ISO-8859-1")+".txt"); 方式二:可以对中文文件名使用url编码,如headers.add("Content-disposition","attachment;filename="+URLEncoder.encode("中国","UTF-8")+".txt"); 疑问:中文文件名转换成ASCII后传给浏览器,浏览器遇到一堆ASCII,如何能正确的还原出来我们原来的中文文件名的呢? 有三种方法:new String(,ISO-8859-1) 、urlencoder 、fileName*=UTF-8‘‘、 ------------------------------------------------ Web applications that want to force a resource to be downloaded rather than directly rendered in a Web browser issue a Content-Disposition header in the HTTP response of the form: Content-Disposition: attachment; filename=FILENAME The filename parameter can be used to suggest a name for the file into which the resource is downloaded by the browser. RFC 2183 (Content-Disposition), however, states in section 2.3 (The Filename Parameter) that the file name can only use US-ASCII characters: Current [RFC 2045] grammar restricts parameter values (and hence Content-Disposition filenames) to US-ASCII. We recognize the great desirability of allowing arbitrary character sets in filenames, but it is beyond the scope of this document to define the necessary mechanisms. The parameters "filename" and "filename*" differ only in that "filename*" uses the encoding defined in [RFC5987], allowing the use of characters not present in the ISO-8859-1 character set ([ISO-8859-1]). |
1.3、UserSerivce.java
void exportExcel(List<User> userList, OutputStream outputStream);
1.4、UserServiceImpl.java
public void exportExcel(List<User> userList, OutputStream outputStream) { ExcelUtils.exportUserExcel(userList, outputStream); }
1.5、ExcelUtils.java
package com.rk.tax.utils; import java.io.IOException; import java.io.OutputStream; import java.util.List; import org.apache.poi.hssf.usermodel.HSSFCell; import org.apache.poi.hssf.usermodel.HSSFCellStyle; import org.apache.poi.hssf.usermodel.HSSFFont; import org.apache.poi.hssf.usermodel.HSSFRow; import org.apache.poi.hssf.usermodel.HSSFSheet; import org.apache.poi.hssf.usermodel.HSSFWorkbook; import org.apache.poi.ss.util.CellRangeAddress; import com.rk.tax.entity.User; public class ExcelUtils { /** * 导出用户的所有列表到excel * @param userList 用户列表 * @param outputStream 输出流 */ public static void exportUserExcel(List<User> userList,OutputStream outputStream){ try { //1、创建工作簿 HSSFWorkbook workbook = new HSSFWorkbook(); //1.1、创建合并单元格对象 CellRangeAddress cellRangeAddress = new CellRangeAddress(0, 0, 0, 4); //1.2、头标题样式 HSSFCellStyle titleStyle = createCellStyle(workbook,(short)16); //1.3、列标题样式 HSSFCellStyle columnHeaderStyle = createCellStyle(workbook,(short)13); //2、创建工作表 HSSFSheet sheet = workbook.createSheet("用户列表"); //2.1、加载合并单元格对象 sheet.addMergedRegion(cellRangeAddress); //设置默认列宽 sheet.setDefaultColumnWidth(25); //3、创建行 //3.1、创建头标题行;并且设置头标题 HSSFRow titleRow = sheet.createRow(0); HSSFCell titleCell = titleRow.createCell(0); //加载单元格样式 titleCell.setCellStyle(titleStyle); titleCell.setCellValue("用户列表"); //3.2、创建列标题行;并且设置列标题 HSSFRow columnHeaderRow = sheet.createRow(1); String[] titles = {"用户名","账号","所属部门","性别","电子邮箱"}; for(int i=0;i<titles.length;i++){ HSSFCell columnHeaderCell = columnHeaderRow.createCell(i); //加载单元格样式 columnHeaderCell.setCellStyle(columnHeaderStyle); columnHeaderCell.setCellValue(titles[i]); } //4、操作单元格;将用户列表写入excel if(userList != null){ for(int j=0;j<userList.size();j++){ HSSFRow row = sheet.createRow(j+2); HSSFCell dataCell0 = row.createCell(0); dataCell0.setCellValue(userList.get(j).getName()); HSSFCell dataCell1 = row.createCell(1); dataCell1.setCellValue(userList.get(j).getAccount()); HSSFCell dataCell2 = row.createCell(2); dataCell2.setCellValue(userList.get(j).getDept()); HSSFCell dataCell3 = row.createCell(3); dataCell3.setCellValue(userList.get(j).isGender()?"男":"女"); HSSFCell dataCell4 = row.createCell(4); dataCell4.setCellValue(userList.get(j).getEmail()); } } //5、输出 workbook.write(outputStream); workbook.close(); } catch (IOException e) { e.printStackTrace(); } } /** * 创建单元格样式 * @param workbook 工作簿 * @param fontSize 字体大小 * @return */ private static HSSFCellStyle createCellStyle(HSSFWorkbook workbook, short fontSize) { HSSFCellStyle style = workbook.createCellStyle(); style.setAlignment(HSSFCellStyle.ALIGN_CENTER);//水平居中 style.setVerticalAlignment(HSSFCellStyle.VERTICAL_CENTER);//垂直居中 //创建字体 HSSFFont font = workbook.createFont(); font.setBoldweight(HSSFFont.BOLDWEIGHT_BOLD);//加粗字体 font.setFontHeightInPoints(fontSize); //加载字体 style.setFont(font); return style; } }
2、从Excel导入用户信息
2.1、UserAction.java
//导入用户列表 public String importExcel(){ //1、获取文件,并判断是否为excel文件 if(userExcel != null && userExcelFileName.matches("^.+\\.(?i)((xls)|(xlsx))$")){ //2、导入 userService.importExcel(userExcel,userExcelFileName); } return "list"; }
2.2、UserSerivce.java
void importExcel(File userExcel, String userExcelFileName);
2.3、UserSerivceImpl.java
public void importExcel(File userExcel, String userExcelFileName) { try { FileInputStream fileInputStream = new FileInputStream(userExcel); boolean is03Excel = userExcelFileName.matches("^.+\\.(?i)(xls)$"); Workbook workbook = is03Excel ? new HSSFWorkbook(fileInputStream) : new XSSFWorkbook(fileInputStream); Sheet sheet = workbook.getSheetAt(0); if(sheet.getPhysicalNumberOfRows()>2){ User user = null; for(int k=2;k<sheet.getPhysicalNumberOfRows();k++) { Row row = sheet.getRow(k); user = new User(); //用户名 Cell cell0 = row.getCell(0); user.setName(cell0.getStringCellValue()); //账号 Cell cell1 = row.getCell(1); user.setAccount(cell1.getStringCellValue()); //所属部门 Cell cell2 = row.getCell(2); user.setDept(cell2.getStringCellValue()); //性别 Cell cell3 = row.getCell(3); user.setGender(cell3.getStringCellValue().equals("男")); //手机号 String mobile = ""; Cell cell4 = row.getCell(4); try { mobile = cell4.getStringCellValue(); } catch (Exception e) { double dMobile = cell4.getNumericCellValue(); mobile = BigDecimal.valueOf(dMobile).toString(); } user.setMobile(mobile); //邮箱 Cell cell5 = row.getCell(5); user.setEmail(cell5.getStringCellValue()); //生日 Cell cell6 = row.getCell(6); if(cell6.getDateCellValue() != null) { user.setBirthday(cell6.getDateCellValue()); } //默认用户密码为123456 user.setPassword("123456"); //默认用户状态为 有效 user.setState(User.USER_STATE_VALID); //5、保存 save(user); } workbook.close(); fileInputStream.close(); } } catch (Exception e) { e.printStackTrace(); } }