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



我在这里多次看到类似的问题,但我不确定它们是否适用于我的案例,或者我只是不理解这个过程。

我有一个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>即可。

为了防止其他标签消失,请将身份模板添加到您的剧本

原因是元素的内置模板:

  • 不"复制"打开和关闭标签
  • 它只是将模板应用于它们的子级,包括文本节点

您必须覆盖此项,包括标识模板

相关内容

  • 没有找到相关文章

最新更新