【发布时间】:2012-05-23 14:28:25
【问题描述】:
作为我对这个问题的思考模式的延续:Saxon in Java: XSLT for CSV to XML
根据 Michael Kay 对该问题的回答,我最终得到了以下代码,用于将 XSLT 应用于文档:
Processor processor = new Processor(false);
StringWriter stringWriter = new StringWriter();
Serializer serializer = new Serializer(stringWriter);
XsltCompiler compiler = processor.newXsltCompiler();
XsltExecutable executable = compiler.compile(new StreamSource(new File(transformLocation)));
XsltTransformer transformer = executable.load();
transformer.setInitialTemplate(new QName("main"));
transformer.setParameter(new QName("filePath"), new XdmAtomicValue("location/of/Test.csv"));
transformer.setDestination(serializer);
transformer.transform();
String transformedDocument = stringWriter.toString().trim();
此代码使用 Saxon 中的 s9api(我使用的是 9.4 HE 版本)。它允许我设置初始模板并动态注入要转换的文档的路径,这允许我转换非 XML 文件(例如 CSV,在这种特殊情况下)。
然而,这在某种程度上抹杀了我的代码重用性。
让我解释一下:我有一个transformDocument() 方法。最初,在我尝试做一些疯狂的事情(例如转换 CSV 并且只使用 XML)之前,我的 marshalObjectToDocument() 和 unmarshalDocumentToObject() 方法都调用了它(有可重用性)。
这是给定一个只有 XML 的世界的两个方向的比较:
-
unmarshalDocumentToObject()- 我从一个包含文档的文件开始。
- 我这样做:
new StreamSource(new File(documentLocation)) - 这个
StreamSource可以作为“源”(XsltTransformer.setSource()) 传递给transformDocument。
-
marshalObjectToDocument()- 我从某种对象开始。
- 这被编组为一个巨大的 XML 字符串。
- 我这样做:
new StreamSource(new StringReader(giantStringOfXML)) - 这个
StreamSource可以作为“源”(XsltTransformer.setSource()) 传递给transformDocument。
在情况 1 (unmarshalDocumentToObject()) 我有一个文件路径进入,所以我可以更改 transformDocument() 以获取文件路径字符串并将其传递,以便它可以手动将其注入 XSLT 参数。这适用于 XML 和纯文本。
在情况 2 (marshalObjectToDocument()) 我没有文件路径。我有一个对象,它被转换为一个包含其 XML 表示的巨型字符串。我无法将文件路径字符串传递给transformDocument(),因为我没有文件。现在我不能使用transformDocument()。代码重用性被破坏。
我的目标是能够以某种方式在代码中以相同的方式处理 XML 和纯文本文档,并且能够重用我的代码来应用 XSLT 和 XSD,无论我是在编组还是解组。这是一个不切实际的目标吗?我是否注定要为每种文档类型和方向编写不同的代码?或者有人可以解决这个问题吗?
【问题讨论】:
标签: java xml xslt saxon plaintext