0

我正在创建一个 XSL 来格式化来自我正在集成的 API 的一些传入 XML。我收到的 xml 如下所示:

<items>
  <item xmlns="http://www.tempuri.org/Item.xsd">
    <key>value</key>
  </item>
  <item>
    <key>value</key>
  </item>
  <item xmlns="http://www.tempuri.org/Item.xsd">
    <key>value</key>
  </item>
</items>

一些“item”节点定义了“xmlns”属性,而另一些则没有。当我尝试遍历我的 XSL 中的结果时,它没有找到定义了 xmlns 属性的节点。

<xsl:for-each select="item">
  <xsl:value-of select="key" />
</xsl:for-each>

我对整个 XSL 有点陌生,所以我不确定我做错了什么。

4

2 回答 2

1

您需要在定义中定义相同的命名空间<xsl:stylesheet>

然后:

<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:ns="http://www.tempuri.org/Item.xsd"
    extension-element-prefixes="exsl"
    encoding="utf-8">

. . .

<xsl:for-each select="item|ns:item">
    <xsl:value-of select="key|ns:key"/>
</xsl:for-each>

确实,您应该尝试对相同的事物使用相同的命名空间。

于 2010-01-25T18:51:11.843 回答
0

首先,如果您不了解 XML 名称空间的工作原理以及它们的含义,那么您将遇到无穷无尽的问题。您正在努力解决的这个问题只是冰山一角。

也就是说,您可以按照 Kyle Butt 建议的方式处理名称空间,将转换范围的前缀映射分配到stylesheet元素中的名称空间,然后在 XPath 表达式中使用前缀。

但是如果你不知道命名空间怎么办?然后你必须使用更钝的工具:

<xsl:for-each select="*[local-name()='item']">
  <xsl:value-of select="*[local-name()='key']"/>
</xsl:for-each>

使用local-name()完全忽略命名空间。但是您不能在节点测试中使用它(必须是一个名称 likefoo或限定名称 like x:foo),您只能在谓词中使用它。这就是为什么不可爱*[local-name()='foo']是唯一的方法。

于 2010-01-27T08:14:35.563 回答