zoukankan      html  css  js  c++  java
  • EasyPOI 教程以及完整工具类的使用

    因为项目的原因需要用到POI来操作Excel 文档,以前都是直接使用POI来操作的,但是最近听到easypoi的存在,所以自己简单的尝试了下! 别说,他还真的挺好用的

    Easypoi介绍

    Easypoi 为谁而开发

    不太熟悉poi的
    不想写太多重复太多的
    只是简单的导入导出的
    喜欢使用模板的
    都可以使用easypoi

    Easypoi的目标是什么 Easypoi的目标不是替代poi,而是让一个不懂导入导出的快速使用poi完成Excel和word的各种操作,而不是看很多api才可以完成这样工作

    为什么会写Easypoi

    以前的以前(岁月真TMD的快)我虽然写了不少代码但还是很少写poi,然后跳到一家公司之后就和业务人员聊上了,来这个需要个报表,这个报表样式是这样的,这个表头是这样的,就这样我写了大量的poi代码,每次都是大量的篇幅,copy to copy,无聊的一逼,然后加入了jeecg,jeecg中有一个小的工具类,虽然我也不知道是谁写的,然是可以用注解搞定最简单的导出,突然豁然开朗,我可以完善,让我从报表的苦海当中脱离出来,这样我花了一周的时间做了第一个版本支持导入导出放到了jeecg,发现还是不错的,慢慢的用的人越来越多,我就把这块独立出来了,再然后有人提出了模板,然后就加入了模板功能,提出了word的需求,加入了word的功能,后来工作忙了虽然没再参与jeecg,但还是一直维持这easypoi的更新,根据见识的增长也不断的重构这代码,直到现在

    独特的功能

    基于注解的导入导出,修改注解就可以修改Excel
    支持常用的样式自定义
    基于map可以灵活定义的表头字段
    支持一堆多的导出,导入
    支持模板的导出,一些常见的标签,自定义标签
    支持HTML/Excel转换,如果模板还不能满足用户的变态需求,请用这个功能
    支持word的导出,支持图片,Excel
    使用

    1.easypoi 父包--作用大家都懂得
    2.easypoi-annotation 基础注解包,作用与实体对象上,拆分后方便maven多工程的依赖管理
    3.easypoi-base 导入导出的工具包,可以完成Excel导出,导入,Word的导出,Excel的导出功能
    4.easypoi-web 耦合了spring-mvc 基于AbstractView,极大的简化spring-mvc下的导出功能
    5.sax 导入使用xercesImpl这个包(这个包可能造成奇怪的问题哈),word导出使用poi-scratchpad,都作为可选包了
    如果不使用spring mvc的便捷福利,直接引入easypoi-base 就可以了,easypoi-annotation

    如果使用maven,请使用如下坐标

    <dependency>
    <groupId>cn.afterturn</groupId>
    <artifactId>easypoi-base</artifactId>
    <version>3.1.0</version>
    </dependency>
    <dependency>
    <groupId>cn.afterturn</groupId>
    <artifactId>easypoi-web</artifactId>
    <version>3.1.0</version>
    </dependency>
    <dependency>
    <groupId>cn.afterturn</groupId>
    <artifactId>easypoi-annotation</artifactId>
    <version>3.1.0</version>
    </dependency>
    注解

    注解介绍

    easypoi起因就是Excel的导入导出,最初的模板是实体和Excel的对应,model--row,filed--col 这样利用注解我们可以和容易做到excel到导入导出 经过一段时间发展,现在注解有5个类分别是

    @Excel 作用到filed上面,是对Excel一列的一个描述
    @ExcelCollection 表示一个集合,主要针对一对多的导出,比如一个老师对应多个科目,科目就可以用集合表示
    @ExcelEntity 表示一个继续深入导出的实体,但他没有太多的实际意义,只是告诉系统这个对象里面同样有导出的字段
    @ExcelIgnore 和名字一样表示这个字段被忽略跳过这个导导出
    @ExcelTarget 这个是作用于最外层的对象,描述这个对象的id,以便支持一个对象可以针对不同导出做出不同处理
    @Excel

    这个是必须使用的注解,如果需求简单只使用这一个注解也是可以的,涵盖了常用的Excel需求,需要大家熟悉这个功能,主要分为基础,图片处理,时间处理,合并处理几块,name_id是上面讲的id用法,这里就不累言了

    属性 类型 默认值 功能
    name

    String

    null

    列名,支持name_id

    needMerge

    boolean

    fasle

    是否需要纵向合并单元格(用于含有list中,单个的单元格,合并list创建的多个row)

    orderNum

    String

    "0"

    列的排序,支持name_id

    replace

    String[]

    {}

    值得替换 导出是{a_id,b_id} 导入反过来

    savePath

    String

    "upload"

    导入文件保存路径,如果是图片可以填写,默认是upload/className/ IconEntity这个类对应的就是upload/Icon/

    type

    int

    1

    导出类型 1 是文本 2 是图片,3 是函数,10 是数字 默认是文本

    width

    double

    10

    列宽

    height

    double

    10

    列高,后期打算统一使用@ExcelTarget的height,这个会被废弃,注意

    isStatistics

    boolean

    fasle

    自动统计数据,在追加一行统计,把所有数据都和输出 这个处理会吞没异常,请注意这一点

    isHyperlink

    boolean

    false

    超链接,如果是需要实现接口返回对象

    isImportField

    boolean

    true

    校验字段,看看这个字段是不是导入的Excel中有,如果没有说明是错误的Excel,读取失败,支持name_id

    exportFormat

    String

    ""

    导出的时间格式,以这个是否为空来判断是否需要格式化日期

    importFormat

    String

    ""

    导入的时间格式,以这个是否为空来判断是否需要格式化日期

    format

    String

    ""

    时间格式,相当于同时设置了exportFormat 和 importFormat

    databaseFormat

    String

    "yyyyMMddHHmmss"

    导出时间设置,如果字段是Date类型则不需要设置 数据库如果是string 类型,这个需要设置这个数据库格式,用以转换时间格式输出

    numFormat

    String

    ""

    数字格式化,参数是Pattern,使用的对象是DecimalFormat

    imageType

    int

    1

    导出类型 1 从file读取 2 是从数据库中读取 默认是文件 同样导入也是一样的

    suffix

    String

    ""

    文字后缀,如% 90 变成90%

    isWrap

    boolean

    true

    是否换行 即支持

    mergeRely

    int[]

    {}

    合并单元格依赖关系,比如第二列合并是基于第一列 则{0}就可以了

    mergeVertical

    boolean

    fasle

    纵向合并内容相同的单元格

    fixedIndex

    int

    -1

    对应excel的列,忽略名字

    isColumnHidden

    boolean

    false

    导出隐藏列

    @ExcelTarget

    限定一个到处实体的注解,以及一些通用设置,作用于最外面的实体

    属性 类型 默认值 功能
    value

    String

    null

    定义ID

    height

    double

    10

    设置行高

    fontSize

    short

    11

    设置文字大小

    @ExcelEntity

    标记是不是导出excel 标记为实体类,一遍是一个内部属性类,标记是否继续穿透,可以自定义内部id

    属性 类型 默认值 功能
    id

    String

    null

    定义ID

    @ExcelCollection

    一对多的集合注解,用以标记集合是否被数据以及集合的整体排序

    属性 类型 默认值 功能
    id

    String

    null

    定义ID

    name

    String

    null

    定义集合列名,支持nanm_id

    orderNum

    int

    0

    排序,支持name_id

    type

    Class<?>

    ArrayList.class

    导入时创建对象使用

    @ExcelIgnore

    忽略这个属性,多使用需循环引用中,无需多解释吧^^

     接下来就是实战了:

    首先是实体类:

    接下来是工具类的编写:

    package com.example.easypoi.util;

    import cn.afterturn.easypoi.excel.ExcelExportUtil;
    import cn.afterturn.easypoi.excel.ExcelImportUtil;
    import cn.afterturn.easypoi.excel.entity.ExportParams;
    import cn.afterturn.easypoi.excel.entity.ImportParams;
    import cn.afterturn.easypoi.excel.entity.enmus.ExcelType;
    import org.apache.commons.lang3.StringUtils;
    import org.apache.poi.ss.usermodel.Workbook;
    import org.springframework.web.multipart.MultipartFile;

    import javax.servlet.http.HttpServletResponse;
    import java.io.File;
    import java.io.IOException;
    import java.net.URLEncoder;
    import java.util.List;
    import java.util.Map;
    import java.util.NoSuchElementException;

    /**
    * @Auther: lijiawei
    * @Date: 2018/7/23 12:08
    * @Description: Excle 文件导入导出Util(easypoi)
    */
    public class EasyPoiUtil {
    /**
    * 功能描述:复杂导出Excel,包括文件名以及表名。创建表头
    *
    * @author 李家威
    * @date 2018/7/23 13:07
    * @param list 导出的实体类
    * @param title 表头名称
    * @param sheetName sheet表名
    * @param pojoClass 映射的实体类
    * @param isCreateHeader 是否创建表头
    * @param fileName
    * @param response
    * @return
    */
    public static void exportExcel(List<?> list, String title, String sheetName, Class<?> pojoClass, String fileName, boolean isCreateHeader, HttpServletResponse response) {
    ExportParams exportParams = new ExportParams(title, sheetName);
    exportParams.setCreateHeadRows(isCreateHeader);
    defaultExport(list, pojoClass, fileName, response, exportParams);
    }


    /**
    * 功能描述:复杂导出Excel,包括文件名以及表名,不创建表头
    *
    * @author 李家威
    * @date 2018/7/23 13:07
    * @param list 导出的实体类
    * @param title 表头名称
    * @param sheetName sheet表名
    * @param pojoClass 映射的实体类
    * @param fileName
    * @param response
    * @return
    */
    public static void exportExcel(List<?> list, String title, String sheetName, Class<?> pojoClass, String fileName, HttpServletResponse response) {
    defaultExport(list, pojoClass, fileName, response, new ExportParams(title, sheetName));
    }

    /**
    * 功能描述:Map 集合导出
    *
    * @author 李家威
    * @date 2018/7/23 16:14
    * @param list 实体集合
    * @param fileName 导出的文件名称
    * @param response
    * @return
    */
    public static void exportExcel(List<Map<String, Object>> list, String fileName, HttpServletResponse response) {
    defaultExport(list, fileName, response);
    }

    /**
    * 功能描述:默认导出方法
    *
    * @author 李家威
    * @date 2018/7/23 15:33
    * @param list 导出的实体集合
    * @param fileName 导出的文件名
    * @param pojoClass pojo实体
    * @param exportParams ExportParams封装实体
    * @param response
    * @return
    */
    private static void defaultExport(List<?> list, Class<?> pojoClass, String fileName, HttpServletResponse response, ExportParams exportParams) {
    Workbook workbook = ExcelExportUtil.exportExcel(exportParams, pojoClass, list);
    if (workbook != null) {
    downLoadExcel(fileName, response, workbook);
    }
    }

    /**
    * 功能描述:Excel导出
    *
    * @author 李家威
    * @date 2018/7/23 15:35
    * @param fileName 文件名称
    * @param response
    * @param workbook Excel对象
    * @return
    */
    private static void downLoadExcel(String fileName, HttpServletResponse response, Workbook workbook) {
    try {
    response.setCharacterEncoding("UTF-8");
    response.setHeader("content-Type", "application/vnd.ms-excel");
    response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
    workbook.write(response.getOutputStream());
    } catch (IOException e) {
    throw new RuntimeException(e);
    }
    }

    /**
    * 功能描述:默认导出方法
    *
    * @author 李家威
    * @date 2018/7/23 15:33
    * @param list 导出的实体集合
    * @param fileName 导出的文件名
    * @param response
    * @return
    */
    private static void defaultExport(List<Map<String, Object>> list, String fileName, HttpServletResponse response) {
    Workbook workbook = ExcelExportUtil.exportExcel(list, ExcelType.HSSF);
    if (workbook != null) ;
    downLoadExcel(fileName, response, workbook);
    }


    /**
    * 功能描述:根据文件路径来导入Excel
    *
    * @author 李家威
    * @date 2018/7/23 14:17
    * @param filePath 文件路径
    * @param titleRows 表标题的行数
    * @param headerRows 表头行数
    * @param pojoClass Excel实体类
    * @return
    */
    public static <T> List<T> importExcel(String filePath, Integer titleRows, Integer headerRows, Class<T> pojoClass) {
    //判断文件是否存在
    if (StringUtils.isBlank(filePath)) {
    return null;
    }
    ImportParams params = new ImportParams();
    params.setTitleRows(titleRows);
    params.setHeadRows(headerRows);
    List<T> list = null;
    try {
    list = ExcelImportUtil.importExcel(new File(filePath), pojoClass, params);
    } catch (NoSuchElementException e) {
    throw new RuntimeException("模板不能为空");
    } catch (Exception e) {
    e.printStackTrace();

    }
    return list;
    }

    /**
    * 功能描述:根据接收的Excel文件来导入Excel,并封装成实体类
    *
    * @author 李家威
    * @date 2018/7/23 14:17
    * @param file 上传的文件
    * @param titleRows 表标题的行数
    * @param headerRows 表头行数
    * @param pojoClass Excel实体类
    * @return
    */
    public static <T> List<T> importExcel(MultipartFile file, Integer titleRows, Integer headerRows, Class<T> pojoClass) {
    if (file == null) {
    return null;
    }
    ImportParams params = new ImportParams();
    params.setTitleRows(titleRows);
    params.setHeadRows(headerRows);
    List<T> list = null;
    try {
    list = ExcelImportUtil.importExcel(file.getInputStream(), pojoClass, params);
    } catch (NoSuchElementException e) {
    throw new RuntimeException("excel文件不能为空");
    } catch (Exception e) {
    throw new RuntimeException(e.getMessage());

    }
    return list;
    }


    }
    下面是测试类以及结果:

    就此,easypoi 的工作就完成了 是不是很简单

    更多教程可以参考官方APIhttp://easypoi.mydoc.io/#text_202979
    ---------------------
    作者:HiBoyljw
    来源:CSDN
    原文:https://blog.csdn.net/HiBoyljw/article/details/81170802
    版权声明:本文为博主原创文章,转载请附上博文链接!

  • 相关阅读:
    learnyou 相关网站
    hdu 3038 How Many Answers Are Wrong
    hdu 3047 Zjnu Stadium 并查集高级应用
    poj 1703 Find them, Catch them
    poj 1182 食物链 (带关系的并查集)
    hdu 1233 还是畅通工程
    hdu 1325 Is It A Tree?
    hdu 1856 More is better
    hdu 1272 小希的迷宫
    POJ – 2524 Ubiquitous Religions
  • 原文地址:https://www.cnblogs.com/wangsongbai/p/10493783.html
Copyright © 2011-2022 走看看