【问题标题】:Adding Xinclude support to an XSLT stylesheet将 Xinclude 支持添加到 XSLT 样式表
【发布时间】:2013-02-13 09:09:02
【问题描述】:

我有一个大型 XSLT 样式表,可以将 XML 格式转换为 HTML。我想在输入 XML 文件中添加对 XInclude 的支持。目标是每个包含文件以及包含 XML 文件都可以独立进行 XSD 验证。我控制了 XML 模式中的所有更改(我认为);只有特定的 XML 元素可以移出到包含文件中,并且只有一层包含文件嵌套。我在 Eclipse 的 XML 编辑器中工作,它很好地验证了包含文件和每个包含文件。

XSLT 样式表有两种使用方式,在这里我们更接近我的问题:

  1. 在使用 lxml 进行 XSLT 转换的 Python 脚本的构建环境中。 Python 脚本被集成到基于 make 的构建环境和 Eclipse 的 Ant 脚本中。

  2. 在包含 XML 文件的 xsl 样式表指令中。这适用于人们希望在 Web 浏览器中立即查看他们在任何 XML 文件中所做的更改的情况。到目前为止,这已被证明是一个非常有效的环境,所以我不想放弃它。

我能够通过在 Python 脚本中使用 ElementTree.xinclude() 方法来获得用例 1。但是,这不是用例 2 的解决方案。

另外,我知道如何编写一个只执行 Xinclude 解析的 XSLT 样式表,理论上这可以用作第一个转换,然后是现有的 XSLT 样式表,用于 XML 到 HTML 的转换。问题是 XML 文件只能有一个 xsl-stylesheet 指令。

另一个想法是将 XInclude 分辨率留给 Web 浏览器。但是,我不知道有任何 Web 浏览器支持该功能。另外,我不希望限制只使用一种特定的浏览器。到目前为止,我们支持所有最常见的浏览器。

另一个想法是将 XInclude 解析支持添加到现有的 XSLT 样式表中。但是,我在为输入和输出而苦苦挣扎,因为这实际上是三个阶段(文件中的 XML 输入 -> 带有 Xinclude 解析的 FLat XML -> HTML。XInclude 解析部分需要执行第一次转换并且现有的 XSLT 代码将执行第二个。我不确定在一个样式表中是否可行。

我的问题是:

  1. 有什么方法可以在使用 Web 浏览器打开(包括)XML 文件时调用两个 XSLT 样式表?

  2. 有什么方法可以改进现有的 XSLT 样式表并支持 XInclude 以使其保持单一样式表?

  3. XSLT 样式表中有什么方法可以修改输入吗?

  4. Web 浏览器是否支持 XInclude 分辨率?

谢谢 安迪

【问题讨论】:

    标签: xslt xinclude


    【解决方案1】:

    1 有什么方法可以让我调用两个 XSLT 样式表 使用 Web 浏览器打开(包括)XML 文件?

    2 有什么办法可以改进现有的 XSLT 样式表 XInclude 支持使其保持单个样式表?

    [3] XSLT 样式表中是否有任何方法可以修改输入?

    [4] Web 浏览器是否支持 XInclude 解析?

    以相反的顺序处理问题,因为这样更容易:

    (4) 我还没有看到任何进行 XInclude 扩展的网络浏览器。

    (3) 我不知道“修改输入”是什么意思:XSLT 转换 (或修改)输入为输出。除非你问:可以 您一步修改输入,然后再次转换输出 再次 ?是:如果浏览器支持 exslt:node-set,那么您可以 使用一次转换的结果创建一个变量,然后选择 该变量用于另一个变换。您可以使用模式来选择 不同步骤的不同模板集。

    类似:

     <xsl:variable name="doc.all">
        <xsl:apply-templates  mode="p1" select="/" />
    </xsl:variable>
    

    带有一组 mode="p1" 模板,以及某处 选择该变量作为节点集的模板:

      <xsl:template match="/" >
        <xsl:apply-templates select="exslt:node-set($doc.all)" />
      </xsl:template>
    

    [ XSLT-2.0 可以更直接地处理节点集,但是没有浏览器 原生支持 XSLT-2.0]

    (2) 我不知道您现有的样式表是什么样的,但可能:是的。 当您认为它必然是两个独立的时,您是在程序上思考 执行 XInclude 处理和 xslt 其余部分的步骤。如果你正在做 XInclude 使用 XSLT 扩展,那么 xinclude 只是另一组要匹配的模式。

    你可能想要类似这个模板的东西来做 xinclude 扩展:

       <xsl:template   match="xi:include[@href][@parse='xml' or not(@parse)]">
            <xsl:apply-templates select="document(@href)/*" />  
        </xsl:template>
    

    modified from the answer to this question : 在文档后添加“/*”(@href) 避免在包含的文档以及基础上再次调用根模板 文档。

    然后包含一个 match="/" 模板来设置外部 html,其余的 创建内部节点的转换模式。

    这两个步骤在这里是隐含的:第一步是将输入源重定向到 xi:include/@href 遇到该元素时。 Step to 是处理节点 根据其他匹配模板在该文档中。

    (1) 您只能使用 PI 运行一个样式表,但是,您有 浏览器中的Javascript,所以只要你避免跨域安全问题,你应该 能够按程序做事。

    需要考虑的几点:

    我不知道如果作为一个转换的结果,您生成另一个具有不同指令的文件,浏览器会做什么。它又继续了吗?可能值得一试。如果没有,您可以在 javascript 中显式进行处理,然后应用第二次转换。

    您的浏览器支持 xslt、javascript 和 css:您可以将 javascript 和 css 注入到输出中。并且 css 可以为 XML 和 HTML 设置样式。

    Michael Kay 发布了Saxon CE,这是一个编译成 javascript 的 XSLT 2.0 实现,因此它可以在浏览器中运行。

    【讨论】:

      【解决方案2】:

      您可能应该看看 XProc 来做到这一点

      您的用例似乎过于复杂,无法在单个 XSLT 中完成

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2015-05-31
        • 1970-01-01
        • 2016-08-08
        • 2021-12-14
        • 1970-01-01
        • 2021-06-16
        • 2012-09-26
        相关资源
        最近更新 更多