spring boot 导出数据到excel


手把手教你springboot中导出数据到excel中

问题来源:

前一段时间公司的项目有个导出数据的需求,要求能够实现全部导出也可以多选批量导出(虽然不是我负责的,我自己研究了研究),我们的项目是xboot前后端分离系统,后端的核心为SpringBoot 2.2.6.RELEASE,因此今天我主要讲述后端的操作实现,为了简化需求,我将需要导出的十几个字段简化为5个字段,导出的样式模板如下:

实现步骤:

打开一个你平时练习使用的springboot的demo,开始按照以下步骤加入代码进行操作。

1.添加maven依赖

1
2
3
4
5
6
<!--Excel-->
<dependency>
     <groupId>org.apache.poi</groupId>
     <artifactId>poi-ooxml</artifactId>
     <version> 3.11 </version>
</dependency>   

 poi-ooxml是一个excel表格的操作工具包,处理的单页数据量也是百万级别的,因此我们选择的是poi-ooxml.

2.编写excel工具类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
import  org.apache.poi.ss.usermodel.Cell;
import  org.apache.poi.ss.usermodel.Row;
import  org.apache.poi.ss.usermodel.Sheet;
import  org.apache.poi.xssf.streaming.SXSSFWorkbook;
import  javax.servlet.http.HttpServletResponse;
import  java.io.IOException;
import  java.io.OutputStream;
import  java.io.UnsupportedEncodingException;
import  java.util.List;
 
public  class  ExcelUtil {
     /**
      * 用户信息导出类
      * @param response 响应
      * @param fileName 文件名
      * @param columnList 每列的标题名
      * @param dataList 导出的数据
      */
     public  static  void  uploadExcelAboutUser(HttpServletResponse response,String fileName,List<String> columnList,<br>List<List<String>> dataList){
         //声明输出流
         OutputStream os =  null ;
         //设置响应头
         setResponseHeader(response,fileName);
         try  {
             //获取输出流
             os = response.getOutputStream();
             //内存中保留1000条数据,以免内存溢出,其余写入硬盘
             SXSSFWorkbook wb =  new  SXSSFWorkbook( 1000 );
             //获取该工作区的第一个sheet
             Sheet sheet1 = wb.createSheet( "sheet1" );
             int  excelRow =  0 ;
             //创建标题行
             Row titleRow = sheet1.createRow(excelRow++);
             for ( int  i =  0 ;i<columnList.size();i++){
                 //创建该行下的每一列,并写入标题数据
                 Cell cell = titleRow.createCell(i);
                 cell.setCellValue(columnList.get(i));
             }
             //设置内容行
             if (dataList!= null  && dataList.size()> 0 ){
                 //序号是从1开始的
                 int  count =  1 ;
                 //外层for循环创建行
                 for ( int  i =  0 ;i<dataList.size();i++){
                     Row dataRow = sheet1.createRow(excelRow++);
                     //内层for循环创建每行对应的列,并赋值
                     for ( int  j = - 1 ;j<dataList.get( 0 ).size();j++){ //由于多了一列序号列所以内层循环从-1开始
                         Cell cell = dataRow.createCell(j+ 1 );
                         if (j==- 1 ){ //第一列是序号列,不是在数据库中读取的数据,因此手动递增赋值
                             cell.setCellValue(count++);
                         } else { //其余列是数据列,将数据库中读取到的数据依次赋值
                             cell.setCellValue(dataList.get(i).get(j));
                         }
                     }
                 }
             }
             //将整理好的excel数据写入流中
             wb.write(os);
         catch  (IOException e) {
             e.printStackTrace();
         finally  {
             try  {
                 // 关闭输出流
                 if  (os !=  null ) {
                     os.close();
                 }
             catch  (IOException e) {
                 e.printStackTrace();
             }
         }
     }
 
     /*
         设置浏览器下载响应头
      */
     private  static  void  setResponseHeader(HttpServletResponse response, String fileName) {
         try  {
             try  {
                 fileName =  new  String(fileName.getBytes(), "ISO8859-1" );
             catch  (UnsupportedEncodingException e) {
                 e.printStackTrace();
             }
             response.setContentType( "application/octet-stream;charset=UTF-8" );
             response.setHeader( "Content-Disposition" "attachment;filename=" + fileName);
             response.addHeader( "Pargam" "no-cache" );
             response.addHeader( "Cache-Control" "no-cache" );
         catch  (Exception ex) {
             ex.printStackTrace();
         }
     }
}

 网上的excel的工具类有很多,但很多并不是你复制过来就能直接使用的,因此需要我们深究其原理,这样可以应对不同的场景写出属于我们自己的合适的代码,这里就不一一解释了,代码中注释加的很清楚,有不懂的可以留言评论。

3.编写controller,service,serviceImpl,dao,entity

3.1 entity

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
import  io.swagger.annotations.ApiModelProperty;
import  lombok.Data;
import  org.hibernate.annotations.Where;
import  javax.persistence.*;
import  java.math.BigDecimal;
 
@Data
@Entity
@Where (clause =  "del_flag = 0" )
@Table (name =  "t_scf_item_data" )
public  class  ItemData{
     private  static  final  long  serialVersionUID = 1L;
 
     @Id
     @TableId
     @ApiModelProperty (value =  "唯一标识" )
     private  String id = String.valueOf(SnowFlakeUtil.getFlowIdInstance().nextId());
 
     @ApiModelProperty (value =  "创建者" )
     @CreatedBy
     private  String createBy;
 
     @CreatedDate
     @JsonFormat (timezone =  "GMT+8" , pattern =  "yyyy-MM-dd HH:mm:ss" )
     @DateTimeFormat (pattern =  "yyyy-MM-dd HH:mm:ss" )
     @ApiModelProperty (value =  "创建时间" )
     private  Date createTime;
    
     @ApiModelProperty (value =  "项目编号" )
     private  String itemNo;
     @ApiModelProperty (value =  "项目名称" )
     private  String itemName;
     
     @ApiModelProperty (value =  "删除标志 默认0" )
     private  Integer delFlag =  0 ;   
}

 3.2 dao

1
2
3
4
5
6
7
8
9
10
11
12
import  cn.exrick.xboot.modules.item.entity.ItemData;
import  org.springframework.data.jpa.repository.Query;
import  org.springframework.stereotype.Repository;
import  java.util.List;
 
@Repository
public  interface  ItemDataDao{
   @Query (value =  "select a.item_no,a.item_name,concat(a.create_time),a.create_by from t_scf_item_data a where a.del_flag = 0 limit 5" ,nativeQuery =  true )
     List<List<String>> findAllObject();
     @Query (value =  "select a.item_no,a.item_name,concat(a.create_time),a.create_by  from t_scf_item_data a where a.del_flag = 0 and a.id in ?1 limit 5" ,nativeQuery =  true )
     List<List<String>> findByIds(List<String> idList);
}

 3.3 service

1
2
3
4
5
6
import  javax.servlet.http.HttpServletResponse;
import  java.util.List;
 
public  interface  TestService {
     void  exportExcel(List<String> idList, HttpServletResponse response);
}

 3.4 serviceImpl

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
import  cn.exrick.xboot.common.utils.ExcelUtil;
import  cn.exrick.xboot.modules.item.dao.ItemDataDao;
import  cn.exrick.xboot.modules.item.service.TestService;
import  org.springframework.beans.factory.annotation.Autowired;
import  org.springframework.stereotype.Service;
import  org.springframework.transaction.annotation.Transactional;
import  javax.servlet.http.HttpServletResponse;
import  java.util.ArrayList;
import  java.util.Arrays;
import  java.util.List;
 
@Transactional
@Service
public  class  TestServiceImpl  implements  TestService {
 
     @Autowired
     private  ItemDataDao itemDataDao;
     @Override
     public  void  exportExcel(List<String> idList, HttpServletResponse response) {
         List<List<String>> dataList =  new  ArrayList<>();
         if (idList ==  null  || idList.size() ==  0 ){
               dataList = itemDataDao.findAllObject();
         } else {
               dataList = itemDataDao.findByIds(idList);
         }
         List<String> titleList = Arrays.asList( "序号" , "项目编码" "项目名称" "创建时间" "创建人" );
         ExcelUtil.uploadExcelAboutUser(response, "apply.xlsx" ,titleList,dataList);
     }
}

 3.5 controller

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
import  cn.exrick.xboot.modules.item.service.TestService;
import  io.swagger.annotations.ApiOperation;
import  lombok.extern.slf4j.Slf4j;
import  org.springframework.beans.factory.annotation.Autowired;
import  org.springframework.web.bind.annotation.RequestBody;
import  org.springframework.web.bind.annotation.RequestMapping;
import  org.springframework.web.bind.annotation.RequestMethod;
import  org.springframework.web.bind.annotation.RestController;
 
import  javax.servlet.http.HttpServletResponse;
import  java.util.List;
import  java.util.Map;
@Slf4j
@RestController
@RequestMapping ( "/test" )
public  class  TestController {
 
     @Autowired
     private  TestService testService;
 
     @RequestMapping (value =  "/exportExcel" , method = RequestMethod.POST)
     @ApiOperation (value =  "导出excel" ,produces= "application/octet-stream" )
     public  void  exportCorpLoanDemand( @RequestBody  Map<String,List<String>> map, HttpServletResponse response){ ;
         log.info( "测试:{}" ,map);
         testService.exportExcel(map.get( "list" ),response);
     }
}

 

4.测试

测试的话可以使用swagger或者postman,甚至你前端技术足够ok的话也可以写个简单的页面进行测试,我是用的是swaager进行的测试,下面就是我测试的结果了:

 

 

 

 

 

原文链接:https://www.cnblogs.com/zaevn00001/p/13353744.html?utm_source=tuicool


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM