本文记录一下用Apache POI操作Excel时可能遇到一些坑。

excel版本错误

首先是excel版本问题,由于office excel 03版和07版的区别,在读取文件时如果版本不匹配会报以下错误。

org.apache.poi.poifs.filesystem.NotOLE2FileException: Invalid header signature; read 0x0010000000060809, expected 0xE11AB1A1E011CFD0 - Your file appears not to be a valid OLE2 documentat org.apache.poi.poifs.storage.HeaderBlock.<init>(HeaderBlock.java:167)at org.apache.poi.poifs.storage.HeaderBlock.<init>(HeaderBlock.java:106)at org.apache.poi.poifs.filesystem.POIFSFileSystem.<init>(POIFSFileSystem.java:137)at org.apache.poi.hssf.usermodel.HSSFWorkbook.<init>(HSSFWorkbook.java:382)at org.apache.poi.hssf.usermodel.HSSFWorkbook.<init>(HSSFWorkbook.java:364)

最初解决办法是根据文件名采用不同的Workbook来初始化stream,大致代码如下,请忽视判断逻辑不严谨的问题(这里应该取后缀名而不是判断包含)。

            if (filePath.indexOf(".xlsx") != -1) {XSSFWorkbook wb = new XSSFWorkbook(inputStream);return wb.getSheetAt(sheetIndex);} else {HSSFWorkbook wb = new HSSFWorkbook(inputStream);return wb.getSheetAt(sheetIndex);}

手动修改文件名后不匹配

通过上面的方法大部分还是可以解决的,但是遇到人为改变后缀名后会出现如下异常。

Caused by: org.apache.poi.openxml4j.exceptions.InvalidFormatException: Package should contain a content type part [M1.13]at org.apache.poi.openxml4j.opc.ZipPackage.getPartsImpl(ZipPackage.java:203)at org.apache.poi.openxml4j.opc.OPCPackage.getParts(OPCPackage.java:684)at org.apache.poi.openxml4j.opc.OPCPackage.open(OPCPackage.java:275)at org.apache.poi.util.PackageHelper.open(PackageHelper.java:37)

再次优化一下,使用工厂模式创建Workbook:

Workbook workbook = WorkbookFactory.create(inputStream);

看一下POI的源码:

public static Workbook create(InputStream inp, String password) throws IOException, InvalidFormatException, EncryptedDocumentException {InputStream is = FileMagic.prepareToCheckMagic(inp);FileMagic fm = FileMagic.valueOf(is);switch(fm) {case OLE2:NPOIFSFileSystem fs = new NPOIFSFileSystem(is);return create(fs, password);case OOXML:return new XSSFWorkbook(OPCPackage.open(is));default:throw new InvalidFormatException("Your InputStream was neither an OLE2 stream, nor an OOXML stream");}}

可以看到他是根据stream类型来初始化的,这样即使人为改变文件名也无关紧要。

stream类型错误

通过上面的方式处理后,有时候还是会出现以下异常:

org.apache.poi.openxml4j.exceptions.InvalidFormatException: Your InputStream was neither an OLE2 stream, nor an OOXML streamat org.apache.poi.ss.usermodel.WorkbookFactory.create(WorkbookFactory.java:186)at org.apache.poi.ss.usermodel.WorkbookFactory.create(WorkbookFactory.java:149)at com.github.crab2died.ExcelUtils.readExcel2Objects(ExcelUtils.java:126)at com.github.crab2died.ExcelUtils.readExcel2Objects(ExcelUtils.java:206)

这个问题可能是文件传输stream为非可读性的stream,解决方法为将读取的stream转为ByteArrayInputStream再读取:

InputStream is = new ByteArrayInputStream(xlsxInByteArray);

然而笔者是直接读取本地文件,并非此类问题,以下解答给了笔者答案,直接文件另存为后再读取新的文件,问题解决。

https://stackoverflow.com/questions/29894185/your-inputstream-was-neither-an-ole2-stream-nor-an-ooxml-stream-while-reading

如果文件很多,直接在程序中先另写一个文件再读取新文件即可,目前没有找到更好的解决方案。

Apache POI操作Excel的坑相关推荐

  1. Apache POI操作Excel导出JAVABEAN对象方法

    2019独角兽企业重金招聘Python工程师标准>>> Apache POI操作Excel导出方法说明 Apache的POI组件是Java操作Microsoft Office办公套件 ...

  2. Apache POI操作Excel文件

    Apache POI是用Java编写的免费开源的跨平台的Java API,Apache POI提供API给Java程序对Microsoft Office格式档案读和写的功能,其中使用最多的就是使用PO ...

  3. 如何用Apache POI操作Excel文件-----如何对一个单元格加注解?

    有的时候,我们需要通过操作Apache POI,在生成Cell数据的同时,能对其生成的Cell,加上注解(comments),类似于下面的. 那么对于这种情况,我们的代码应该如何写呢? 借花献佛,我就 ...

  4. Apache POI 操作Excel常用方法

    文章目录 一.Apache POI 介绍 二.Apache POI中的常用方法 1.新建工作簿和工作表 1.新建工作簿 2.新建工作表 3.打开一个excel 4.将excel输出 2.创建单元格 1 ...

  5. (6) 如何用Apache POI操作Excel文件-----POI-3.10的一个和注解(comment)相关的另外一个bug...

    如果POI-3.10往一个工作表(sheet)里面插入数据的话,需要注意了,其有一个不太被容易发现的bug. 被插入的工作表(sheet)里面的单元格没有包含任何的注解(comment)的时候,插入一 ...

  6. 如何用Apache POI操作Excel文件-----如何在已有的Excel文件中插入一行新的数据?

    在POI的第一节入门中,我们提供了两个简单的例子,一个是如何用Apache POI新建一个工作薄,另外一个例子是,如果用Apache POI新建一个工作表.那么在这个章节里面,我将会给大家演示一下,如 ...

  7. 如何用Apache POI操作Excel文件-----如何用Apache POI 画一个离散图

    有的时候,我们需要Excel中的数据,通过一个图画,可视化的表现出来. 那么这个时候,应该如何做呢?现在就借花献佛,以Apache POI自己提供的一个例子为例,给大家演示一下POI的API 如何画图 ...

  8. java使用poi操作excel文件_使用 java apache poi 操作 excel xlsx 文件

    工作中临时需要对各种订单量进行简单的统计分析,为了方便简单学习了apache poi 对 xlsx 文件的基本操作,简单记录 1. 引包 org.apache.poi poi-ooxml 4.1.2 ...

  9. 采用APACHE POI操作EXCEL文件--计算式调用另一文件

    http://blog.sina.com.cn/s/blog_6151984a0100sczi.html 测试环境: 当前EXCEL文件: workbook.xls 假设一个CELL的计算式如下:   ...

最新文章

  1. python27安装-二、Python2.7的安装并与Python3.8共存
  2. webapp支持什么数据库_数据库和Webapp安全
  3. one hot 编码的实现
  4. 高德地图入驻广州交警 实现“互联网+交通”无缝对接
  5. Swift和Object-C的区别和优缺点
  6. springboot+vue整合百度的Ueditor(保姆级教程)
  7. “没拿到一毛钱股份的老公”刷爆朋友圈 吃瓜群众雾里看花
  8. 最新版WIN10安装教程(官方纯净版)(适用于新机以及旧机重装系统或升级系统)
  9. Lua二进制chunk
  10. Oracle的异构数据迁移工具 - OMW及ODI
  11. HDU 2022 海选女主角
  12. java反转字符串的方法
  13. 想转行做程序员?转行不难,难的是以后不后悔。
  14. 车载导航产品的数字地图格式
  15. 如何查看电脑的 CPU 信息 ?
  16. python常用常用函数
  17. 【SPSS】激素水平项目实战案例
  18. 【VBA】一行代码删除所有空行
  19. Elasticsearch 多语言及中文分词与检索详解
  20. 新一代虚拟驾驶仿真平台

热门文章

  1. python的itertools库_Python标准库itertools模块使用方法
  2. 蓝桥杯 基础练习 时间转换
  3. Android自定义view之基础知识
  4. cts测试linux指令skip,linux – dd命令中seek和skip之间有什么区别?
  5. c++ 遍历list_小白学PyTorch | 6 模型的构建访问遍历存储(附代码
  6. linux系统中存放用户账号信息的文件是,信息安全技术题库:Linux系统中,用户登录密码的hash是存放在()文件中的。...
  7. IIS部署VUE刷新404问题如何解决?
  8. pandas根据索引删除dataframe列
  9. Spring Boot与JWT整合实现前后端分离的用户认证
  10. JavaScript 之call , apply 和prototype 介绍