Springboot は POI を統合して、どこでも Excel レポートの例を実現します

1. POIの紹介

詳細については、この記事を参照してください
https://blog.csdn.net/w893932747/article/details/89354979

2. POI実装エクスポート例

springboot プロジェクトで Excel ファイルをエクスポートするために poi を統合するインターフェイスの例を書いてみましょう

1. 環境の準備

最初に springboot プロジェクトを準備します。ここでは例は示しません
。 springboot プロジェクトの下に poi の依存関係を導入します。例として 3.17 バージョンを示します。

<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi</artifactId>
    <version>3.17</version>
</dependency>
<dependency>
    <groupId>org.apache.poi</groupId>
    <artifactId>poi-ooxml</artifactId>
    <version>3.17</version>
</dependency>

データの準備として、次のデータをレポート
ここに画像の説明を挿入
データ レポート SQL ファイルとしてエクスポートします:
https://pan.baidu.com/s/1bv0EV1fIhbExD6j0dhlzPw 抽出コード 8qz1

2. Daoレイヤーを作成する

  1. エンティティクラス
public class GoodInfo {
    
    
    private Long spuId;
    private String title;
    private String cname;
    private String brandName;
    private String skuId;
    private String subTitle;
    private String ownSpec;
    private Double price;

    /*Getter Setter自行添加*/
  1. Daoクラス(ここではクエリSQLをアノテーション形式で記述しています)
import com.changgou.item.po.GoodInfo;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Select;
import java.util.List;

@Mapper
public interface PoiDao {
    
    

    @Select("SELECT * FROM `good_info` ORDER BY spu_id LIMIT 200")
    List<GoodInfo> getGoodInfo();
}

2. コントローラー層を作成する

import com.changgou.item.service.PoiService;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;

import javax.servlet.http.HttpServletResponse;

@Controller
@RequestMapping("poi")
public class PoiController {
    
    

    @Autowired
    private PoiService poiService;

    @PostMapping("/export")
    public ResponseEntity<Void> exportGoodInfo(HttpServletResponse response) {
    
    
        poiService.exportGoodInfo(response);
        return ResponseEntity.ok().build();
    }
}

3. サービス層の作成

データ レポート例の最初のいくつかのフィールドの値と最後のいくつかのフィールドの値には 1 対多の関係があるため、各データのフロント部門のフィールドが同じであることがわかります。ここではそれらをグループ化します。この部分の同じフィールドごとにセルを配置し、同じ値の部門フィールドを持つセルを結合します。

import com.alibaba.fastjson.JSONObject;
import com.changgou.item.dao.PoiDao;
import com.changgou.item.po.GoodInfo;
import org.apache.poi.hssf.usermodel.*;
import org.apache.poi.ss.usermodel.FillPatternType;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.apache.poi.ss.util.CellRangeAddress;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletResponse;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.stream.Collectors;

@Service
public class PoiService {
    
    
    private final Logger LOGGER = LoggerFactory.getLogger(this.getClass());

    public static final List<String> GOOD_INFO_COLUMNS = new ArrayList<>(
            Arrays.asList("spu编号", "标题","商品分类","商品品牌","sku编号","详细信息","参数属性","价格")
    );
    public static final List<String> GOOD_COLUMNS = new ArrayList<>(
            Arrays.asList("spuId", "title","cname","brandName","skuId","subTitle","ownSpec","price")
    );

    @Autowired
    private PoiDao poiDao;

    public void exportGoodInfo(HttpServletResponse response) {
    
    
        List<GoodInfo> goodInfoList = poiDao.getGoodInfo();
        // 按spuId分组
        Map<String, List<GoodInfo>> goodInfoMap = goodInfoList.stream()
                .collect(Collectors.groupingBy(item -> item.getSpuId().toString()));
        // 创建一个空的excel表格
        HSSFWorkbook workbook = new HSSFWorkbook();
        // 创建一个sheet页
        HSSFSheet sheet = workbook.createSheet("商品信息列表");
        // 创建表头
        HSSFRow row = sheet.createRow(0);
        // 创建表头格式style对象
        HSSFCellStyle style = workbook.createCellStyle();
        // 创建字体对象
        HSSFFont font = workbook.createFont();
        //字体设置为红色
        font.setColor(IndexedColors.RED.index);
        //字体加粗
        font.setBold(true);
        style.setFont(font);
        // 设置单元格水平居中
        style.setAlignment(HorizontalAlignment.CENTER);
        // 设置单元格填充色
        style.setFillPattern(FillPatternType.SOLID_FOREGROUND);
        style.setFillForegroundColor(IndexedColors.YELLOW.index);
        Map<Integer, Integer> columnWidthMap = new HashMap<>();
        // 写入表头
        for (int i = 0; i< GOOD_INFO_COLUMNS.size(); i++) {
    
    
            // 创建单元格
            HSSFCell cell = row.createCell(i);
            cell.setCellStyle(style);
            // 设置单元格宽度
            sheet.setColumnWidth(i, GOOD_INFO_COLUMNS.get(i).getBytes().length *256);
            // 将表头值字符长度保存到columnWidthMap中
            columnWidthMap.put(i, GOOD_INFO_COLUMNS.get(i).getBytes().length);
            // 设置表有值
            cell.setCellValue(GOOD_INFO_COLUMNS.get(i));
        }
        // 记录正文行号
        int page = 1;
        // 创建正文格式style对象
        style = workbook.createCellStyle();
        style.setAlignment(HorizontalAlignment.CENTER);
        // 遍历正文数据
        for (Map.Entry<String, List<GoodInfo>> entry : goodInfoMap.entrySet()) {
    
    
        	// 记录每组数据起始行数
            int firstRow = page;
            for (GoodInfo goodInfo : entry.getValue()) {
    
    
            	// 创建正文行
                HSSFRow goodRow = sheet.createRow(page);
                Map<String, Object> map = JSONObject.parseObject(JSONObject.toJSONString(goodInfo), Map.class);
                for (int i = 0; i< GOOD_COLUMNS.size(); i++) {
    
    
                    // 创建单元格
                    HSSFCell cell = goodRow.createCell(i);
                    cell.setCellStyle(style);
                    Object object = map.get(GOOD_COLUMNS.get(i));
                    String value = object == null ? "" : object.toString();
                   	// 设置单元格狂歌为字段值最大的宽度
                    int headerLength = columnWidthMap.get(i);
                    int valueLength = value.getBytes().length;
                    int columnWidth = headerLength > valueLength ? headerLength : valueLength;
                    columnWidthMap.put(i, columnWidth);
                    sheet.setColumnWidth(i, columnWidth * 256);
                    cell.setCellValue(value);
                }
                page++;
            }
            // 记录每组数据末尾行数
            int lastRow = firstRow + entry.getValue().size() - 1;
            // 合并相同字段的单元格
            if (firstRow < lastRow) {
    
    
                for (int j = 0; j < 4; j++) {
    
    
                    CellRangeAddress region = new CellRangeAddress(firstRow, lastRow, j, j);
                    sheet.addMergedRegion(region);
                }
            }
        }
        response.setContentType("application/vnd.ms-excel");
        SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");
        String fileName = new String(("goodInfoList" + sdf.format(new Date()) + ".xls"));
        try {
    
    
            OutputStream os = response.getOutputStream();
            response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
            workbook.write(os);
        } catch (Exception e) {
    
    
            LOGGER.error("fail: ", e);
        }
    }

}

4. 最終的なエフェクト表示

次の操作が完了したら、プロジェクトを開始してインターフェイスを呼び出すことができ、最終的なレポート ファイルは次のように表示されます。
ここに画像の説明を挿入

おすすめ

転載: blog.csdn.net/weixin_44947701/article/details/124994288