xsl:result-来自 Altova XML 和 Saxon 的文件的奇怪行为
Strange behavior with xsl:result-document from within Altova XML with Saxon
我的输入文件:
<folders>
<folder name="a" level="1" metadataFile="LVM20metadata.tsv">
<subfolder name="a/er" level="2" filter="no" />
<subfolder name="a/ir" level="2" filter="yes" />
<subfolder name="a/ar" level="2" filter="no" />
<subfolder name="a/or" level="2" filter="yes" />
</folder>
<folder name="b" level="1" metadataFile="LVM21metadata.tsv">
<subfolder name="b/er" level="2" filter="no" />
<subfolder name="b/ir" level="2" filter="yes" />
<subfolder name="b/ar" level="2" filter="no" />
<subfolder name="b/or" level="2" filter="yes" />
</folder>
</folders>
我的样式表:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:fn="http://www.w3.org/2005/xpath-functions " exclude-result-prefixes="fn xs">
<xsl:template match="/">
<xsl:apply-templates/>
</xsl:template>
<xsl:template match="folders">
<xsl:apply-templates/>
</xsl:template>
<xsl:template match="folder">
<xsl:result-document method="xml" standalone="yes" href="{@name}.xml">
<hello></hello>
</xsl:result-document>
</xsl:template>
</xsl:stylesheet>
它不会创建两个结果文档。这是为什么? (使用 saxon9he)
这不是应该创建两个 XML 文件,名称为 a.xml 和 b.xml 吗?
如果您 运行 来自 oXygen 或 Altova 的样式表,这实际上是一个已知功能(或错误,如果您愿意)。我不确定现在的版本是否还有这个 "feature",但它的工作原理如下:
- 如果没有主要结果文档(即生成一个空序列)
- 还有一个次要结果文档(即
xsl:result-document
)
- 在用户界面中显示第一个这样的结果文档
- 让任何其他结果文档正常创建
我认为这是因为这些工具使用某种 UriResolver
来重定向主要结果。如果没有输出,则 UriResolver
不会被调用,但随后会被下一个辅助输出调用,从而导致此行为。这就是为什么这个文件最终出现在你系统的临时文件位置的原因(你会在那里找到带有 "normal" 转换的主要输出文档)。
每当我遇到这种情况并且我不喜欢这种行为时,简单的解决方案就是创建一个虚拟的主要结果文档。在你的情况下,这可能是这样的:
<xsl:template match="/">
<root>Primary result doc, please ignore, see other files.</root>
<xsl:apply-templates/>
</xsl:template>
我相信有一个系统 属性 或环境变量可以用来询问它是否在 UI 中 运行ning,或者如果没有,向设置静态参数的调用命令行添加一个参数(不幸的是,这仅适用于 XSLT 3.0),您可以在 use-when
.
中使用它
我的输入文件:
<folders>
<folder name="a" level="1" metadataFile="LVM20metadata.tsv">
<subfolder name="a/er" level="2" filter="no" />
<subfolder name="a/ir" level="2" filter="yes" />
<subfolder name="a/ar" level="2" filter="no" />
<subfolder name="a/or" level="2" filter="yes" />
</folder>
<folder name="b" level="1" metadataFile="LVM21metadata.tsv">
<subfolder name="b/er" level="2" filter="no" />
<subfolder name="b/ir" level="2" filter="yes" />
<subfolder name="b/ar" level="2" filter="no" />
<subfolder name="b/or" level="2" filter="yes" />
</folder>
</folders>
我的样式表:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:fn="http://www.w3.org/2005/xpath-functions " exclude-result-prefixes="fn xs">
<xsl:template match="/">
<xsl:apply-templates/>
</xsl:template>
<xsl:template match="folders">
<xsl:apply-templates/>
</xsl:template>
<xsl:template match="folder">
<xsl:result-document method="xml" standalone="yes" href="{@name}.xml">
<hello></hello>
</xsl:result-document>
</xsl:template>
</xsl:stylesheet>
它不会创建两个结果文档。这是为什么? (使用 saxon9he)
这不是应该创建两个 XML 文件,名称为 a.xml 和 b.xml 吗?
如果您 运行 来自 oXygen 或 Altova 的样式表,这实际上是一个已知功能(或错误,如果您愿意)。我不确定现在的版本是否还有这个 "feature",但它的工作原理如下:
- 如果没有主要结果文档(即生成一个空序列)
- 还有一个次要结果文档(即
xsl:result-document
) - 在用户界面中显示第一个这样的结果文档
- 让任何其他结果文档正常创建
我认为这是因为这些工具使用某种 UriResolver
来重定向主要结果。如果没有输出,则 UriResolver
不会被调用,但随后会被下一个辅助输出调用,从而导致此行为。这就是为什么这个文件最终出现在你系统的临时文件位置的原因(你会在那里找到带有 "normal" 转换的主要输出文档)。
每当我遇到这种情况并且我不喜欢这种行为时,简单的解决方案就是创建一个虚拟的主要结果文档。在你的情况下,这可能是这样的:
<xsl:template match="/">
<root>Primary result doc, please ignore, see other files.</root>
<xsl:apply-templates/>
</xsl:template>
我相信有一个系统 属性 或环境变量可以用来询问它是否在 UI 中 运行ning,或者如果没有,向设置静态参数的调用命令行添加一个参数(不幸的是,这仅适用于 XSLT 3.0),您可以在 use-when
.