XML元素具有命名空间,我的XPATH无法工作。

14

我收到了以下XML:

<root>
  <items>
    <item>
      <title>Item</title>
      <details>
        <data xmlns="http://some_url">
          <length>10</length>
          <weight>1.2</weight>
        </data>
      </details>
    </item>
  </items>
</root>

下面的XPath不起作用,就像"data"元素不存在一样没有打印任何东西:

/root/items/item/details/data

当我删除"data"元素的"xmlns"命名空间属性时,它的内容就会被输出。 如何编写XPath表达式,以便在不删除"data"元素的"xmlns"命名空间属性的情况下正常工作?

我正在使用SAXON和XSL 1.0。


您需要在XPath引擎中注册名称空间,然后在XPath中使用您注册的别名:alias:data/alias:length。如果不知道您用于评估XPath的工具,我们无法提供更具体的信息。 - Francis Avila
2个回答

16

这是XPath / XSLT中最常见的问题之一:

XPath将未带前缀的元素名称解释为属于“无命名空间”,这就是仅在XPath表达式中指定其未带前缀的名称作为节点测试时,属于默认(非空)命名空间的未带前缀名称元素不被选中的原因。

解决方法要么是:

  1. 创建一个命名空间绑定,将一个前缀(比如说"x")与默认命名空间相关联,然后使用x:elementName而不是elementName来指定元素名称。

  2. 使用冗长、麻烦和不可靠的表达式,例如:*[name() = 'elementName']

这里是使用上述方法1进行的XSLT转换。:

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:a="http://some_url">
 <xsl:output method="text"/>

 <xsl:template match="/">
  <xsl:value-of select=
  "/root/items/item/details/a:data/a:weight"/>
 </xsl:template>
</xsl:stylesheet>

当运用此转换(使用Saxon 6.5.4或其他兼容XSLT 1.0处理器)于所提供的XML文档时

<root>
    <items>
        <item>
            <title>Item</title>
            <details>
                <data xmlns="http://some_url">
                    <length>10</length>
                    <weight>1.2</weight>
                </data>
            </details>
        </item>
    </items>
</root>

选择正确/所需的节点并将其字符串值复制到输出:

1.2

0
在XPath中,您必须为命名空间分配一个前缀。如何做取决于您使用的XPath软件/库,但是假设您将命名空间URI http://some_url 与命名空间前缀someUrl相关联,您可以按以下方式更改XPath表达式:
/root/items/item/details/someUrl:data

谢谢回复。我正在使用SAXON和XSL 1.0。我尝试查询xpath“/ root / items / item / details / a:data”,它打印了“data”元素的所有内容。当我查询“/ root / items / item / details / a:data / a:weight”时,我期望打印“1.2”,但它再次打印了“data”元素的所有内容。请问我做错了什么? - Vojtech
由于您正在使用XSL,请问您能否展示完整的XSL样式表呢?(或者至少是一个相对完整的最小化版本?) - O. R. Mapper

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接