Home > OS >  XPath to select value from namespaced XML using local-name()?
XPath to select value from namespaced XML using local-name()?

Time:12-22

How to extract the value of /substance/text and /makers/text?

I am expecting the result to be

  1. Automation
  2. Test Record

I have tried many things for example:

  • //*[local-name()='text/@value']
  • //*[local-name()='substance']/text/text()
  • //*[local-name()='name'][1]
    (This works for first name element but if I use similar for text it doesn't work.)
  • //*[local-name()='text/@value'][1]
  • //*[local-name()='text'][1]
<health xmlns="http://test.com/sample">
    <substance>
        <name>substance</name>
        <text value="Automation"/>
    </substance>
    <user>
        <reference value="User/111111122"/>
    </user>
    <reaction>
        <makers>
            <name>makers</name>
            <text value="Test Record"/>
        </makers>
    </reaction>
</health>

CodePudding user response:

This XPath,

//*[local-name()='text']/@value

will select all of the value attributes of all text elements in the document, regardless of namespaces.

Note that it is better to account for namespaces than to defeat them in this manner. See How does XPath deal with XML namespaces?


Not working?

The provided XPath does select both @value attributes. If you're only seeing one, it's likely because you're passing the result on to an XPath 1.0 function that expects a single value and is defined to select the first member of a node-set when passed multiple values. See Why does XPath expression only select text of first element?


Still not working?

Here are two options for selecting the values individually rather than collectively:

  1. (//*[local-name()='text']/@value)[1]
    (//*[local-name()='text']/@value)[2]

  2. //*[local-name()='substance']/*[local-name()='text']/@value
    //*[local-name()='makers']/*[local-name()='text']/@value

  • Related