Java easyexcel 导入导出总结

0.前提-----引入依赖


   com.alibaba
   easyexcel
   2.1.1

1.导入

1.实体

package org.mnur.marketing.api.dto.vo;

import com.alibaba.excel.annotation.ExcelProperty;
import lombok.Data;

/**
 * 消息活动-用户导入实体
 */
@Data
public class UserInputVo {

    @ExcelProperty("用户ID")
    private Long consumerId;

    @ExcelProperty("用户手机号")
    private String phone;
}

2.导入模板监听器

package org.mnur.marketing.excel;

import com.alibaba.excel.context.AnalysisContext;
import com.alibaba.excel.event.AnalysisEventListener;
import com.alibaba.excel.exception.ExcelDataConvertException;
import org.hzero.core.exception.MessageException;

import java.util.ArrayList;
import java.util.List;

/**
 * 导入模板监听器
 * @author wy
 * @date 2022-03-14 15:37
 **/
public class UploadDataListener extends AnalysisEventListener {

    /**数据集*/
    private final List list = new ArrayList<>();

    public List getList(){
        return this.list;
    }

    /**
     * 每条数据都会进入
     * @param object:
     * @param analysisContext:
     */
    @Override
    public void invoke(T object, AnalysisContext analysisContext) {
        if(null != analysisContext) {
            this.list.add(object);
        }
    }

    /**
     * 数据解析完调用
     * @param analysisContext:
     */
    @Override
    public void doAfterAllAnalysed(AnalysisContext analysisContext) {

    }

    /**
     * 异常时调用
     * @param exception:
     * @param context:
     * @throws Exception
     */
    @Override
    public void onException(Exception exception, AnalysisContext context) throws Exception {
        // 数据解析异常
        if (exception instanceof ExcelDataConvertException) {
            ExcelDataConvertException excelDataConvertException = (ExcelDataConvertException)exception;
            throw new MessageException("第" + excelDataConvertException.getRowIndex() + "行" + excelDataConvertException.getColumnIndex() + "列" + "数据解析异常");
        }
        // 其他异常...
    }
}

3.业务操作

/**
 * 解析上传文件集合
 * @param urlList 文件地址集合
 * @return 电话号码集合
 */
private HashSet parsingFile(List urlList){
    HashSet hashSet = new HashSet<>();
    urlList.forEach(url->{
        HashSet set = null;
        try {
            set = parsing(getInputStream(url), new UserInputVo(), null);
        } catch (IOException e) {
            e.printStackTrace();
        }
        hashSet.addAll(set);
    });
    return hashSet;
}

/**
 * 文件流解析获取单个上传文件集合
 * @param inputStream 文件流
 * @param vo 对象
 * @param analysisContext analysisContext
 */
public HashSet parsing(InputStream  inputStream, UserInputVo vo, AnalysisContext analysisContext) {
    HashSet hashSet = new HashSet<>();
    UploadDataListener uploadDataListener = new UploadDataListener();
    //开始处理数据
    uploadDataListener.invoke(vo,analysisContext);
    EasyExcelFactory.read(inputStream,UserInputVo.class,uploadDataListener).sheet("Sheet1").doRead();
    List list = uploadDataListener.getList();
    if (CollectionUtils.isEmpty(list)) {
        return hashSet;
    } else {
        list.forEach(vv->{
            hashSet.add(vv.getPhone());
        });
    }
    return hashSet;
}

/**
 * 根据地址获取文件流
 *
 * @param strUrl 文件在线地址
 * @return
 */
private static InputStream getInputStream(String strUrl) throws IOException {
    //把地址转换成URL对象
    URL url = new URL(strUrl);
    //创建http链接
    HttpURLConnection conn = (HttpURLConnection) url.openConnection();
    //设置超时间为3秒
    conn.setConnectTimeout(3 * 1000);
    //防止屏蔽程序抓取而返回403错误
    conn.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");
    //得到输入流
    return conn.getInputStream();
}

4.注意:

本示例传入的是阿里云文件地址集合进行解析

2.导出

1.自定义导出

1.entity

@Data
@NoArgsConstructor
@ApiModel("商品列表导出-列表专用")
public class GoodsVO {

    @ApiModelProperty(value = "商品编码")
    @ExcelProperty(value = "商品编码")
    private String goodsCode;

    @ApiModelProperty(value = "商品全称")
    @ExcelProperty(value = "商品全称")
    private String goodsName;

 }

@Data
@ApiModel("导出列表公用头")
@ColumnWidth(value = 50)
@HeadRowHeight(value = 20)
@ContentRowHeight(value = 18)
public class ExcelHeadVO {

    @ColumnWidth(value = 30)
    @ExcelProperty(value = "项目")
    private String project;

    @ColumnWidth(value = 30)
    @ExcelProperty(value = "内容")
    private String content;

}

2.controller

/**
 * 出接口
 * @param obj 查询参数 type 类型 1:商品  2:点位   3:库存变更  4:交易订单  5:支付订单  6:退款订单
 * @param response 响应
 */
@GetMapping("/export")
@ApiOperation(value = "列表导出(type 类型 1:商品  2:点位   3:库存变更  4:交易订单  5:支付订单  6:退款订单)", httpMethod = "GET")
@Permission(level = ResourceLevel.ORGANIZATION, permissionLogin = true)
public void export(String obj, HttpServletResponse response, @PathVariable String organizationId) {
    exportService.export(response, obj);
}

3.service

/**
 * 导出接口
 * @param response 响应
 * @param obj 对象
 */
void export(HttpServletResponse response, String obj);

4.impl

/*商品库列表*/
private static final String GH = "[{\"project\":\"\",\"content\":\"\"},{\"project\":\"★ 操作信息:\",\"content\":\"\"},{\"project\":\"系统\",\"content\":\"蒙牛新的吧/智能零售运营管理平台\"},{\"project\":\"模块/页面\",\"content\":\"商品/商品库/列表页\"},{\"project\":\"业务操作\",\"content\":\"导出数据\"},{\"project\":\"操作经办\",\"content\":\"\"},{\"project\":\"操作时间\",\"content\":\"\"},{\"project\":\"数据明细数量(条)\",\"content\":\"\"},{\"project\":\"\",\"content\":\"\"},{\"project\":\"★ 数据筛选:\",\"content\":\"\"}]";
/**
 * 导出数据
 * @param response 响应
 * @param obj 对象  type 类型 1:商品  2:点位   3:库存变更  4:交易订单  5:支付订单  6:退款订单
 */
@Override
public void export(HttpServletResponse response,String obj){
    JSONObject jsonObject = JSONObject.parseObject(obj);
    if(null != jsonObject && null != jsonObject.getString("type")) {
        Integer tp = jsonObject.getInteger("type");
        //根据类型判断详情
        switch (tp) {
            case 1:
                this.exportGoodsList(response, obj);
                break;
            default:
                throw new MessageException("导出类型错误", BasePlusConstants.HttpResponseCode.INTERNAL_SERVER_ERROR);
        }
    }
}
/**
 * 导出商品库列表
 * @param obj 查询参数
 */
private void exportGoodsList(HttpServletResponse response,String obj){
    //查询参数
    Goods qo = JSONObject.parseObject(obj , Goods.class) == null ? new Goods() : JSONObject.parseObject(obj , Goods.class);
    //详细数据
    List lit = goodsMapper.queryByCondition(qo);

    //概述
    JSONObject ob = getJsonObject(obj);
    List list = JSON.parseArray(GH, ExcelHeadVO.class);
    getHead(list, CollectionUtils.isEmpty(lit), lit.size());
    //组装查询条件
    ExcelGoodsEnum.getEumValueList().forEach(str->{
        ExcelHeadVO vo = getExcelHeadVO(qo, ob, str);
        list.add(vo);
    });

    try {
        ExcelWriter excelWriter = getExcelWriter(response);
        WriteSheet writeSheet = EasyExcel.writerSheet(0, "操作概要").head(ExcelHeadVO.class).build();
        excelWriter.write(list, writeSheet);
        writeSheet = EasyExcel.writerSheet(1, "数据明细").head(GoodsVO.class).build();
        excelWriter.write(lit, writeSheet);
        excelWriter.finish();
    } catch (Exception e) {
        e.printStackTrace();
    }
}

/**
 * 组装头部信息
 * @param list 集合
 * @param empty 类型
 * @param size 数量
 */
private void getHead(List list, boolean empty, int size) {
    //组装头部变动信息
    Optional.of(list).orElse(new ArrayList<>()).forEach(vv -> {
        if ("操作经办".equals(vv.getProject())) {
            vv.setContent(DetailsHelper.getUserDetails().getUsername());
        }
        if ("操作时间".equals(vv.getProject())) {
            vv.setContent(SDF.format(new Date()));
        }
        if ("数据明细数量(条)".equals(vv.getProject())) {
            vv.setContent(empty ? "0" : size + "");
        }
    });
}

2.模板导出

注意事项:

             1.准备模板

             2.切忌实体类上一样需要注解支持

3.文件地址解析

1.根据本地文件地址解析文件

File file = new File("C:\\Users\\EDY\\Desktop\\mmm.xlsx");
FileItem fileItem = createFileItem(file);
MultipartFile multipartFile = new CommonsMultipartFile(fileItem);

private static FileItem createFileItem(File file) {
    FileItemFactory factory = new DiskFileItemFactory(16, null);
    FileItem item = factory.createItem("textField", "text/plain", true, file.getName());
    int bytesRead = 0;
    byte[] buffer = new byte[8192];
    try {
        FileInputStream fis = new FileInputStream(file);
        OutputStream os = item.getOutputStream();
        while ((bytesRead = fis.read(buffer, 0, 8192)) != -1) {
            os.write(buffer, 0, bytesRead);
        }
        os.close();
        fis.close();
    } catch (IOException e) {
        e.printStackTrace();
    }
    return item;
}

2.根据在线地址解析文件

/**
 * 根据地址获取文件流
 *
 * @param strUrl 文件在线地址
 * @return
 */
private static InputStream getInputStream(String strUrl) throws IOException {
    //把地址转换成URL对象
    URL url = new URL(strUrl);
    //创建http链接
    HttpURLConnection conn = (HttpURLConnection) url.openConnection();
    //设置超时间为3秒
    conn.setConnectTimeout(3 * 1000);
    //防止屏蔽程序抓取而返回403错误
    conn.setRequestProperty("User-Agent", "Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt)");
    //得到输入流
    return conn.getInputStream();
}

/**
     * 获取封装得MultipartFile
     *
     * @param inputStream inputStream
     * @param fileName    fileName
     * @return MultipartFile
     */
    public MultipartFile getMultipartFile(InputStream inputStream, String fileName) {
        FileItem fileItem = createFileItem(inputStream, fileName);
        //CommonsMultipartFile是feign对multipartFile的封装,但是要FileItem类对象
        return new CommonsMultipartFile(fileItem);
    }
 

你可能感兴趣的:(每日学习一个小技术,java,eureka,蓝桥杯)