You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Apache TikaParser抛出不可捕获异常,如何实现捕获处理?

如何捕获Apache Tika处理Excel时的POI单元格格式异常

首先得明确:你外层的try-catch抓不到这个异常,是因为它根本没有向上传播到Tika的parse方法层面。这个异常是POI库在内部处理自定义单元格格式时抛出的,POI自己捕获了它并打印了WARNING日志,但没有把异常抛给上层的Tika调用逻辑,所以你的外层try-catch自然捕获不到。

下面给你两个可行的解决方向,按需选择:

方向一:抑制烦人的WARNING日志(最简单)

如果你的核心需求只是不想看到这个日志输出,直接通过日志框架配置把POI这个类的日志级别调低即可。比如用Logback的话,在logback.xml里加这段配置:

<logger name="org.apache.poi.ss.format.CellFormat" level="OFF"/>

如果用Log4j2,类似地在配置文件里把这个类的日志级别设为ERROR或OFF,这样就不会再打印这个警告了。

方向二:自定义Tika逻辑捕获内部异常(需要代码改造)

如果你需要在异常发生时执行自定义逻辑(比如标记这个文件、记录额外信息),那得自定义Tika处理Excel的逻辑,替换掉默认的Listener来捕获这个异常:

  1. 自定义一个TikaHSSFListener子类,重写formatNumberDateCell方法,捕获里面的异常:
public class CustomTikaHSSFListener extends ExcelExtractor.TikaHSSFListener {
    public CustomTikaHSSFListener(ExcelExtractor extractor, BodyContentHandler handler, Metadata metadata) {
        super(extractor, handler, metadata);
    }

    @Override
    protected void formatNumberDateCell(CellValueRecordInterface cell, String formatString) {
        try {
            // 调用父类逻辑,这里会触发POI的格式处理
            super.formatNumberDateCell(cell, formatString);
        } catch (IllegalArgumentException e) {
            // 在这里捕获你要抓的异常,执行自定义逻辑
            System.err.println("处理单元格格式时出错: " + formatString);
            // 可以选择跳过这个单元格,或者用默认格式处理
            super.handleCellContents(cell.getStringValue());
        }
    }
}
  1. 自定义ExcelExtractor子类,重写创建Listener的方法:
public class CustomExcelExtractor extends ExcelExtractor {
    public CustomExcelExtractor(ParseContext context) {
        super(context);
    }

    @Override
    protected TikaHSSFListener createTikaHSSFListener(BodyContentHandler handler, Metadata metadata) {
        return new CustomTikaHSSFListener(this, handler, metadata);
    }
}
  1. 把自定义的ExcelExtractor注册到Tika的AutoDetectParser里:
    在你的TikaConfiguration初始化代码中,替换默认的OfficeParser逻辑:
// 初始化时,替换默认的OfficeParser
List<Parser> parsers = new ArrayList<>(tikaConfig.getParser());
for (int i = 0; i < parsers.size(); i++) {
    if (parsers.get(i) instanceof OfficeParser) {
        // 创建自定义的OfficeParser,使用我们的ExcelExtractor
        OfficeParser customOfficeParser = new OfficeParser() {
            @Override
            protected ExcelExtractor createExcelExtractor(ParseContext context) {
                return new CustomExcelExtractor(context);
            }
        };
        parsers.set(i, customOfficeParser);
        break;
    }
}
autoDetectParser = new AutoDetectParser(tikaConfig.getDetector(), new CompositeParser(parsers));

这样改造后,当POI抛出那个单元格格式异常时,你就能在自定义Listener的catch块里捕获并处理了。

内容的提问来源于stack exchange,提问作者Stefan Glasenhardt

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 21:57:48