XProc和CDATA

时间:2015-07-15 21:26:21

标签: xml xslt cdata calabash xproc

我有一个XSLT,可以在一个节点内创建一些CDATA。

XML:

<test><inner>stuff</inner></test>

XSLT:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="xs"
    version="2.0">
    <xsl:output method="xml" indent="yes"/>
    <xsl:template match="test">
        <wrapper>
                <xsl:text disable-output-escaping="yes">&lt;![CDATA[</xsl:text>
                <xsl:copy-of select="*"/>
                <xsl:text disable-output-escaping="yes">]]&gt;</xsl:text>
        </wrapper>
    </xsl:template>
</xsl:stylesheet>

这个由Saxon执行的转换返回:

<wrapper><![CDATA[<inner>stuff</inner>]]></wrapper>

我知道我在CDATA中包装XML并且这有点荒谬。但这是我正在使用的API所期望的,所以我别无选择,只能遵循这种模式。

现在我试图将此转换包含在更大的XProc管道中:

<p:pipeline xmlns:p="http://www.w3.org/ns/xproc" version="1.0" >
<p:xslt>
    <p:input port="stylesheet">
        <p:document href="test.xsl" />
    </p:input>
</p:xslt>

返回(使用最新版本的Calabash):

<wrapper>&lt;![CDATA[<inner>stuff</inner>]]&gt;</wrapper>

似乎XProc不遵守disable-output-escaping属性。

我继续尝试了一些XProc函数,包括p:unescape-markup和p:string-replace的各种组合,但我找不到对我的输出的其余部分没有负面影响的解决方案。

我接下来会尝试什么想法?

1 个答案:

答案 0 :(得分:2)

XSLT处理器是not required to support d-o-e

  

XSLT处理器只能禁用输出转义   控制输出结果树的方式。这可能并不总是如此   案件。例如,结果树可以用作源树   另一个XSLT转换而不是输出。

在流水线操作中尤其如此:XSLT可能无法控制输出树的序列化,而只是将其作为DOM或SAX事件传递给管道中的下一步。但即使可以,

  

XSLT处理器   是不需要支持禁用输出转义。如果   xsl:value-of或xsl:text指定输出转义应该是   禁用,XSLT处理器不支持这个,XSLT   处理器可能发出错误信号;如果它没有发出错误信号,那就必须   通过恢复,禁止输出转义

所以你真的不能依赖d-o-e,特别是在管道中。

  

但这是我正在使用的API所期望的,所以我   别无选择,只能遵循这种模式。

我可以同情这种情况,过去使用过错工具因为它们是最好的。但是,CDATA部分的存在(和边界)在XML Infoset中为explicitly not。因此,依赖于CDATA部分的API在其XML输入要求方面存在缺陷。如果它确实依赖于CDATA部分,那么提交有关它的错误报告是个好主意。

另一方面,您正在使用的API可能实际上并不需要CDATA部分;也许它只是要求你提供以某种方式逃脱的XML?如果是这样,还有其他方法可以实现这一点,而不需要XML Infoset之外的特定序列化。如果您可以向我们展示有关API的文档,我们可以帮助确定它实际需要的内容。