0

我用java编写了一个图书数据库应用程序。以 XML 格式存储的书籍。每本书都有一个 XML。书籍可以包含短篇小说,短篇小说可以是 XML。在这种情况下,这本书看起来像:

<?xml version="1.0" encoding="UTF-8"?>
...
<book>
  <content>
    <xi:include  xmlns:xi="http://www.w3.org/2001/XInclude" href="shortStory.xml"/>
  </content>
</book>

因为用户只能上传一个xml,它可以是没有“shortStory.xml”的“book.xml”(之前总是上传shortStory.xml)我需要在没有xinclude的情况下进行XSLT转换。(等情况下两个文件的路径不同)

但是在上传之后(在其他用例中)我需要使用 XInclude 进行 XSLT 转换(这两个文件是相同的路径)

在从 Transformerfactory 获取实例之前,使用 Xinclude 的每个解决方案都设置系统属性:

System.setProperty(
    "org.apache.xerces.xni.parser.XMLParserConfiguration",
    "org.apache.xerces.parsers.XIncludeParserConfiguration"); 

或者使用 DocumentBuilderFactory.setXIncludeAware()。

我想要两个 javax.xml.transform.Transformer 一个设置使用 xinclude,一个不使用。或者一个转换器,但是 javax.xml.transform.stream.StreamSource 的一种简单方法来打开/关闭 xinclude。

谢谢

编辑

试试 Martin Honnen 的解决方案,但是转换有问题,所以我将 SAXreader 更改为 Documentbuilder:

DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
factory.setXIncludeAware(true);
DocumentBuilder docBuilder = factory.newDocumentBuilder();
Document doc = docBuilder.parse(input);
Source source = new DOMSource(doc);
...
transformer.transform(source, result);
4

1 回答 1

0

我认为这更多是与 XML 解析器相关的问题,而不是与 XSLT 处理器相关的问题。根据http://xerces.apache.org/xerces2-j/features.html你可以设置

import javax.xml.parsers.SAXParser;
import org.xml.sax.SAXException;
import org.xml.sax.XMLReader;

SAXParser parser = /* created from SAXParserFactory */;
XMLReader reader = parser.getXMLReader();
try {
    reader.setFeature("http://apache.org/xml/features/xinclude", 
                      true);
} 
catch (SAXException e) {
    System.err.println("could not set parser feature");
}

然后你可以用我认为的那个阅读器构建一个 SAXSource:

SAXSource source = new SAXSource();
source.setXMLReader(reader);

这样,您就可以在打开或关闭 XInclude 的情况下构建源代码,而无需设置系统属性。

于 2014-06-25T16:46:11.610 回答