繁体   English   中英

使用XSLT将XML标签替换为文本节点

[英]Replace XML tag with text node with XSLT

我在这里已经多次询问过类似的问题,但是我不确定它们是否适用于我的案子,或者我只是不理解该过程。

我有一个XML文件,其中包含规则列表:

<rules>
    <rule id="1">
        <block>
            [HTML content]
        </block>
        <block>
            [HTML content]
        </block>
        <block>
            [HTML content]
        </block>
    </rule>
    <rule id="2">
        <block>
            [HTML content]
        </block>
        <block>
            [HTML content]
        </block>
    </rule>
    [...]
</rules>

现在我的代码是这样的:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xhtml="http://www.w3.org/1999/xhtml">
    <xsl:template match="/rules/rule">
        [some output to create the header and title]
        <xsl:for-each select="block">
            <xsl:copy-of select="./node()" />
        </xsl:for-each>
        [some output to create the footer]
    </xsl:template>
</xsl:stylesheet>

需要明确的是,这不是整个文档,而是当用户单击规则以查看内容并且代码被大大简化时通过AJAX调用的部分,必须在内部做出一些决策关于如何显示各种block元素的信息,但是现在这些部分对于我的问题来说是不必要的,只会使阅读代码更加困难。

在这种特殊情况下,XSLT似乎不太合适,因为我直接存储HTML内容,但这是一个更大的项目的一部分,该项目中的数据更加图表化,这实际上是我不得不诉诸此解决方案的唯一部分。

但是,在rule标记中有一些表,这些表使用规则的ID和第二个数字进行编号,例如1-1、1-2,...。问题是,我大约有20条规则,并计划扩展该列表以非线性方式。 现在,我想在规则1和规则2之间添加一条规则,因此我必须更正以下所有表ID。 这已经在过去发生过,并且我相信将来会再次发生。因此,我想避免这种无用的额外工作,并用<id />标记替换静态数字,例如Table <id />-12: [...]并将<id />替换为规则的ID。 我试图以这种方式修改代码:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xhtml="http://www.w3.org/1999/xhtml">
    <xsl:template match="/rules/rule">
        [some output to create the header and title]
        <xsl:for-each select="block">
            <xsl:copy>
                <xsl:apply-templates select="node()|@*" />
            </xsl:copy>
        </xsl:for-each>
        [some output to create the footer]
    </xsl:template>
    <xsl:template match="id"><xsl:value-of select="ancestor::rule/@id" /></xsl:template>
</xsl:stylesheet>

替换有效,唯一的问题是没有像以前的代码那样删除<block>标签,而其他所有标签都消失了。 我只有一个文本块,没有任何HMTL标签。

我无法提出这个解决方案,我是从类似这样的问题中复制出来的,但这是我第一次遇到<xsl:copy><xsl:apply-templates>标记,所以我不是真的确保它们如何工作。 而且,我发现的所有示例都类似于之前链接的示例,在该示例中几乎需要精确的副本。 我还必须在主输出周围添加很多额外的代码,但我不确定它如何与替换交互。

编辑 :我也尝试了变体

            <xsl:apply-templates select="node()|@*">
                <xsl:copy-of select="./node()" />
            </xsl:apply-templates>

for-each循环中,但是我得到了相同的结果:没有标签的文本,但是替换有效。 看起来apply-templates标签删除了所有标签,但是我不知道如何保存它们。

查看您发现的解决方案中的for-each循环:

<xsl:for-each select="block">
    <xsl:copy>
        <xsl:apply-templates select="node()|@*" />
    </xsl:copy>
</xsl:for-each>

在此循环中:

  • <xsl:copy>输出开始标签,实际上是<block>
  • <xsl:apply-templates .../> -“执行”源标记的内容。
  • </xsl:copy>输出结束标记,这次</block>

由于您不需要<block>标签,只需删除<xsl:copy></xsl:copy>

为防止其他标签消失,请将身份模板添加到脚本中。

原因是元素的内置模板:

  • 不会“复制”开始和结束标签,
  • 它仅将模板应用于其子级,包括文本节点。

您必须覆盖它,包括身份模板

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM