4

我有一个使用 xerces API 解析 XML 文档的 java 程序。

我的解析类扩展了 org.apache.xerces.parsers.XMLDocumentParser,重载了 startElement、endElement、characters 方法。

由于是手工编写的复杂 XML 文档(主要是某种配置元素),经典的 xsd 或 dtd 验证是不够的,我必须向用户返回 XML 文档无效。

但是我无法实现的一件事是在错误消息中添加有关当前正在解析的行号(以及为什么不列号)的信息以及发生错误的位置。

我认为这是可能的,因为当 XML 文档不是 XML 有效时解析器生成的异常 (org.apache.xerces.xni.parser.XMLParseException) 包含这些信息。

4

2 回答 2

6

我从来没有用 xerces 尝试过这个,但是 SAX 解析器可以存储一个 SAX Locator,您可以在解析文档时(或在异常之后)从中获取行号和列号。

看起来XMLDocumentParser也许可以做同样的事情。它的父类AbstractXMLDocumentParser有一个startDocument方法,该方法传递了一个XMLLocator参数。如果你重写了这个方法,你可以保存XMLLocator并使用它的getLineNumbergetColumnNumber方法。

于 2009-02-20T17:55:17.727 回答
1

不确定“正确”的方式是什么,但查看 API,假设您提供的 XMLInputSource 采用 InputStream 或 Reader,您可以在使用 LineNumberInputStream 或 LineNumberReader 包装的 InputStream/Reader 中提供,然后查询它的行数字。

例如:

输入流;

流 = ...;

新的 XMLInputSource(流);

会成为:

输入流;
LineNumberInputStream 线流;

流 = ...;
lineStream = new LineNumberInputStream(lineStream);

新的 XMLInputSource(lineStream);

// 现在可以通过 getLineNumber() 询问线路流它在哪一行

我猜您还需要将 LineNumberInputStream/LineNumberReader 传递给扩展 XMLDocumentParser 的类。

不确定所有这些在您的代码中是否可行。

或者深入研究源代码并找出他们是如何做到的。如果您需要访问的变量/方法是私有的,并且您不担心将来会破坏代码,则可以使用反射并删除访问权限来获取它。

于 2009-02-20T16:46:17.830 回答