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


    转自:https://www.cnblogs.com/zaevn00001/p/13353744.html?utm_source=tuicool

    问题来源:

    前一段时间公司的项目有个导出数据的需求,要求能够实现全部导出也可以多选批量导出(虽然不是我负责的,我自己研究了研究),我们的项目是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进行的测试,下面就是我测试的结果了:

     

     如果你觉得这篇博客有用,请点个赞再走吧。

  • 相关阅读:
    HDU 3389 Game (阶梯博弈)
    HDU1536&&POJ2960 S-Nim(SG函数博弈)
    HDU 2089 不要62(数位DP)
    ACdream 1210 Chinese Girls' Amusement(高精度)
    CodeForces 659D Bicycle Race (判断点是否为危险点)
    HDU 4549 (费马小定理+矩阵快速幂+二分快速幂)
    手动删除Win7系统服务列表中残留服务的操作步骤
    C++学习37 string字符串的访问和拼接
    C++学习36 string类和字符串
    C++学习35 模板中的函数式参数
  • 原文地址:https://www.cnblogs.com/sharpest/p/14951077.html
Copyright © 2020-2023  润新知