いま、XMLをApache Digesterでパースするコードを書いているのですが、
(それにしても、DigesterのAPIはホントにわかりづらいなぁ…メソッド名が直感的じゃないというか)
not well-formedなXMLを読ませようとすると、
org.xml.sax.SAXParseException: The element type "data" must be terminated by the matching end-tag "</data>". at org.apache.xerces.util.ErrorHandlerWrapper.createSAXParseException(Unknown Source) at org.apache.xerces.util.ErrorHandlerWrapper.fatalError(Unknown Source) at org.apache.xerces.impl.XMLErrorReporter.reportError(Unknown Source) at org.apache.xerces.impl.XMLErrorReporter.reportError(Unknown Source) at org.apache.xerces.impl.XMLScanner.reportFatalError(Unknown Source) at org.apache.xerces.impl.XMLDocumentFragmentScannerImpl.scanEndElement(Unknown Source) at org.apache.xerces.impl.XMLDocumentFragmentScannerImpl$FragmentContentDispatcher.dispatch(Unknown Source) at org.apache.xerces.impl.XMLDocumentFragmentScannerImpl.scanDocument(Unknown Source) at org.apache.xerces.parsers.XML11Configuration.parse(Unknown Source) at org.apache.xerces.parsers.XML11Configuration.parse(Unknown Source) at org.apache.xerces.parsers.XMLParser.parse(Unknown Source) at org.apache.xerces.parsers.AbstractSAXParser.parse(Unknown Source) at org.apache.xerces.jaxp.SAXParserImpl$JAXPSAXParser.parse(Unknown Source) at org.apache.commons.digester.Digester.parse(Digester.java:1785) ...
と怒られます。まあ当たり前だな、と思っていたのですが、ここでふと疑問が。
SAXって、not well-formedなドキュメントを読ませると、必ずエラーを返してくれるのでしょうか?
つまり、SAXパーサーはwell-formednessの検証をしてくれるのか?ということです。
少なくともjavadocを見る限りでは、「not well-formedなドキュメントを読ませると、絶対にエラーにするよ」
と明言している箇所は見当たらず。
ソースを読む
うーむ。めんどくさいけどXercesのソースを読んでみるか。
………見つけた。
org.apache.xerces.impl.XMLDocumentFragmentScannerImpl#scanEndElement
で閉じタグのチェックをしていました。
protected int scanEndElement() throws IOException, XNIException { ... //REVISIT: if the string is not the same as expected.. we need to do better error handling.. //We can skip this for now... In any case if the string doesn't match -- document is not well formed. if (!fEntityScanner.skipString(fElementQName.rawname)) { reportFatalError("ETagRequired", new Object[]{fElementQName.rawname}); } ... } // scanEndElement():int
XMLDocumentFragmentScannerImplでは、このほかにも各種チェックを行っている模様です。
事実上の標準であるXerces以外を使うことはまずありえません。今回のプロジェクトに限ったことではなく。
なのでSAXでもwell-formedであることの検証はしているのだ、と考えてもよさそうです。