一篇读懂利用poi将Excel导入到数据库,将数据库导出到Excel
前言
这两天在做Excel的导入及导出,查询了很多资料才完成,作了好多难,在搜寻的过程中,发现网上的资源很乱,没有一篇是非常舒服的,所以我想写篇文章试试,如果成功对后来者有帮助,我会感到十分荣幸!!!提示:以下是本篇文章正文内容,
使用步骤
1.引入pom依赖
代码如下:
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>5.0.0</version>
</dependency>
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi</artifactId>
<version>5.0.0</version>
</dependency>
2.写poi工具类
代码如下:
package com.cy.util;
import com.cy.pojo.Merch;
import org.apache.poi.hpsf.DocumentSummaryInformation;
import org.apache.poi.hpsf.SummaryInformation;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.FillPatternType;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.multipart.MultipartFile;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.List;
/**
* 工具类,用于文件上传、下载、解析
* @author zhang
*/
public class PoiUtils {
/**
* 将对象集合导出到excel
* @param list
* @param <T>
* @return
*/
public static <T> ResponseEntity<byte[]> exportToExcel(List<T> list) {
// 1、创建一个excel文档
HSSFWorkbook workbook = new HSSFWorkbook();
// 2、创建文档摘要
workbook.createInformationProperties();
// 3、获取并配置文档摘要信息
DocumentSummaryInformation docInfo = workbook.getDocumentSummaryInformation();
// 文档类别
docInfo.setCategory("文档类别");
// 文档管理员
docInfo.setManager("PostGirl");
// 设置公司信息
docInfo.setCompany("www.postgirl.com");
// 4、获取文档摘要信息
SummaryInformation summaryInformation = workbook.getSummaryInformation();
// 文档标题
summaryInformation.setTitle("文档标题");
// 文档作者
summaryInformation.setAuthor("PostGirl");
// 备注信息
summaryInformation.setComments("本文档由 PostGirl 提供");
// 5、创建样式
// 创建标题行的样式
HSSFCellStyle headerStyle = workbook.createCellStyle();
headerStyle.setFillForegroundColor(IndexedColors.GREEN.getIndex()); // 背景颜色
headerStyle.setFillPattern(FillPatternType.SOLID_FOREGROUND); // 填充模式
HSSFSheet sheet = workbook.createSheet();// 不传name 默认为sheet1
// 6、创建标题行 第一行数据
// 只循环一次目的是将对象名写入到excel标题上
for (T t : list) {
HSSFRow row = sheet.createRow(0);
String[] fieldNames = getFiledNames(t);
for (int i=0; i<fieldNames.length; i++) {
HSSFCell cell = row.createCell(i);
cell.setCellValue(fieldNames[i]);
cell.setCellStyle(headerStyle);
}
break;
}
// 7、创建后面行
for (int j=0; j<list.size(); j++) {
T t = list.get(j);
String[] fieldValues = getFieldValues(t);
// 由于第一行已经写入了标题,所以这里从第二行开始写
HSSFRow rows = sheet.createRow(j+1);
for (int i=0; i<fieldValues.length; i++) {
rows.createCell(i).setCellValue(fieldValues[i]);
}
}
ByteArrayOutputStream baos = new ByteArrayOutputStream();
HttpHeaders headers = new HttpHeaders();
try {
// 防止乱码
headers.setContentDispositionFormData("attachment",new String("系统导出文件.xls".getBytes("UTF-8"),"ISO-8859-1"));
headers.setContentType(MediaType.APPLICATION_OCTET_STREAM);
workbook.write(baos);
} catch (IOException e) {
e.printStackTrace();
}
return new ResponseEntity<byte[]>(baos.toByteArray(),headers, HttpStatus.CREATED);
}
/**
* 传入文件,解析并返回实体集合,用于后续操作
* @param file
* @return
*/
其中Merch是我的实体类,你可以换成你的实体类
public static List<Merch> excelToEntity (MultipartFile file) {
List<Merch> list = new ArrayList<>();
Merch merch = null;
try {
// 1、创建一个workbook对象
HSSFWorkbook workbook = new HSSFWorkbook(file.getInputStream());
// 2、获取workboot中表单的数量
int numberOfSheets = workbook.getNumberOfSheets();
for (int i=0; i<numberOfSheets; i++) {
// 3、获取sheet页
HSSFSheet sheet = workbook.getSheetAt(i);
// 4、获取sheet页中的行数
int physicalNumberOfRows = sheet.getPhysicalNumberOfRows();
for (int j=0; j<physicalNumberOfRows; j++) {
if (j==0) {
continue; // 跳过标题行
}
// 6、获取行
HSSFRow row = sheet.getRow(j);
if (row == null) {
continue; // 防止数据中间有空行
}
// 7、获取列数
int physicalNumberOfCells = row.getPhysicalNumberOfCells();
这边的也需要换
merch = new Merch();
for (int k=0; k<physicalNumberOfCells; k++) {
HSSFCell cell = row.getCell(k);
switch (k) {
下面的也需要换,set和get是你实体类的set,get方法
根据你的具体实体类进行更改
case 1:
merch.setName(cell.getStringCellValue());
break;
case 2:
merch.setCode(cell.getStringCellValue());
break;
case 3:
merch.setFactory(cell.getStringCellValue());
break;
case 4:
merch.setPackaging(cell.getStringCellValue());
break;
case 5:
merch.setPrice(cell.getNumericCellValue());
break;
case 6:
merch.setStock((int) cell.getNumericCellValue());
break;
default:
break;
}
}
list.add(merch);
}
}
} catch (IOException e) {
e.printStackTrace();
}
return list;
}
/**
* 获取所有对象属性名称
* @param o
* @return
*/
public static String[] getFiledNames(Object o) {
Field[] fields=o.getClass().getDeclaredFields();
String[] fieldNames=new String[fields.length];
for(int i=0;i<fields.length;i++){
fieldNames[i]=fields[i].getName();
}
return fieldNames;
}
/**
* 获取对象属性值
* @param o
* @return
* @throws NoSuchMethodException
* @throws InvocationTargetException
* @throws IllegalAccessException
*/
private static String[] getFieldValues(Object o) {
Field[] fields=o.getClass().getDeclaredFields();
String[] fieldNames=new String[fields.length];
String[] fieldValues = new String[fieldNames.length];
for(int i=0;i<fields.length;i++){
fieldNames[i]=fields[i].getName();
}
try {
for (int i=0; i<fieldNames.length; i++) {
String fieldName = fieldNames[i];
String field = o.getClass().getMethod("get" + returnFirstCapital(fieldName)).invoke(o).toString();
fieldValues[i] = field;
}
} catch(Exception e) {
}
return fieldValues;
}
/**
* 判断字符串首字母是否为大写,如果不是转化为大写
* @param str
* @return
*/
public static String returnFirstCapital(String str) {
if (str.charAt(0) >= 'A' && str.charAt(0) <= 'Z') {
return str;
}
char[] ch = str.toCharArray();
ch[0] -= 32;
return String.valueOf(ch);
}
}
3.写XXXController层
代码如下:
@Autowired
private MerchService merchService;
/**
* 导入
*
* @param merch
* @return
*/
@RequestMapping("/importExcel")
public String saveMerch(MultipartFile file, Merch merch) {
List<Merch> merches = PoiUtils.excelToEntity(file);
//saveAll.(merches)添加
merchService.saveAll(merches);
return "redirect:/index";
}
4.写XXXService层
代码如下:
void saveAll(List<Merch> merches);
5.写XXXServiceImpl实现层
代码如下:
@Override
public void saveAll(List<Merch> merches) {
加强for循环遍历使List<Merch> merches 能转换成merch实体类
for (Merch merch : merches) {
这里
System.out.println("ID:" + merch.getId() + " name:" + merch.getName() + " Code:" + merch.getCode() + " Factory:" + merch.getFactory()
+ "Pagkaging:" + merch.getPackaging() + "Price:" + merch.getPrice() + "Stock:" + merch.getStock());
到这里是为了让你在控制台看的输入些,可以删除,
下面这个就是添加的方法
merchMapper.insertSelective(merch);
}
}
6.写XXXMapper
这里我用的是XXXMapper.xm映射,所以我写了XXXMapper.xml
int insertSelective(Merch merch);
7.写XXXMapper.xml
这里我用的是XXXMapper.xm映射,所以我写了XXXMapper.xml
<insert id="insertSelective"> 这里的id和Mapper层的对应
insert into merch 这里的merch是你的数据库
(id,name,code,factory,packaging,price,stock)这里是你数据库的字段
values
下面的一一对应,id我的是自增所以我设置的是null
(null,#{name},#{code},#{factory},#{packaging},#{price},#{stock})
</insert>
8.前端html
提供种方法有好多中写法
action="/importExcel"访问路径这个要和Controller的@RequestMapping("/importExcel")一样
<input type="button" value="导出" onclick="location.href='/exceExport'">
<form action="/importExcel" method="post" enctype="multipart/form-data">
<input type="file" class="btn btn-primary" size="60" name="file" id="file"/>
<input type="submit" class="btn btn-primary fa fa-search" size="60" value="批量导入">
</form>
css自己设置或者添加到自己原来的里面自己修改。
总结
本篇的导入已经测试完毕,导出还没测试,因为我用了另一种方法,如果本篇文章有帮到你一点忙的话,感到十分荣幸!!!