PDFBox 2.0.19读取客户PDF报错:引用长度对象类型错误求助
问题根源
这个PDF文件不符合PDF规范,其中编号为9的对象被错误定义为字典格式<< 4476 >>,但按照PDF标准,流对象的Length属性对应的对象必须是数字或指向数字对象的引用。普通PDF阅读器自带容错机制能忽略这类错误,但PDFBox的解析逻辑更严格,因此触发了Wrong type of referenced length object异常。
解决方法
方法一:手动修复PDF文件
直接修改错误的对象定义:
- 用文本编辑器(如Notepad++)打开PDF文件,找到
9 0 obj << 4476 >> endobj这一行 - 将其修改为
9 0 obj 4476 endobj,保存后再用PDFBox读取即可正常解析
方法二:自定义PDFBox解析逻辑添加容错
如果无法修改源文件,可以通过重写PDFBox的解析类来处理这种异常情况:
- 继承
COSParser类,重写getLength方法 - 在方法中增加判断:当遇到类型为
COSDictionary的Length对象时,尝试提取字典中的数字值作为长度
示例代码:
public class TolerantCOSParser extends COSParser { public TolerantCOSParser(RandomAccessRead source) throws IOException { super(source); } @Override protected long getLength(COSBase lengthObject) throws IOException { if (lengthObject instanceof COSDictionary) { COSDictionary dict = (COSDictionary) lengthObject; // 提取字典中的数字值,这里假设字典内只有一个数字项 for (COSBase value : dict.values()) { if (value instanceof COSInteger) { return ((COSInteger) value).longValue(); } } // 如果提取失败,再抛出原异常 throw new IOException("Wrong type of referenced length object: " + lengthObject); } return super.getLength(lengthObject); } }
之后使用自定义的解析器来加载PDF:
try (RandomAccessFile raf = new RandomAccessFile("your-file.pdf", "r"); RandomAccessRead source = new RandomAccessFileRAF(raf)) { TolerantCOSParser parser = new TolerantCOSParser(source); parser.parse(); COSDocument cosDoc = parser.getDocument(); PDDocument document = new PDDocument(cosDoc); // 后续操作 } catch (IOException e) { e.printStackTrace(); }
方法三:升级PDFBox到最新版本
检查PDFBox的最新版本是否已针对这类容错场景做了优化,升级到最新稳定版后可能无需额外处理即可读取该文件。
内容的提问来源于stack exchange,提问作者lin
相关产品推荐
相关产品推荐

