0

I have some XML that looks like this:

<contacts>
    <person>
        <name>Bob</name>
        <phoneNumber>1234</phoneNumber>
        <mobileNumber>5678</mobileNumber>
        <address>Address 1</address>
    </person>
    <person>
        <name>Sue</name>
        <phoneNumber>4321</phoneNumber>
        <address>Address 2</address>
    </person>
</contacts>

And some Xpath that queries for all the child nodes of <person>:

//name | //phoneNumber | //mobileNumber | //address

The result is this:

Bob
1234
5678
Address 1
Sue
4321
Address 2

I would like the Xpath query to return something (a string?) so that I can identify which <person> is missing a child node (in this case the second person has no <mobileNumber>.

The output I would like would look something like this:

Bob
1234
5678
Address 1
Sue
4321
null
Address 2

Thanks and let me know if you need more details!

UPDATE

The expression must be valid for Xpath 1.0 as I am using javascript's document.evaluate.

UPDATE

I have got some of the way with this expression:

concat(substring(/contacts/person/mobileNumber, 1 div boolean(/contacts/person/mobileNumber)),substring('null', 1 div not(/contacts/person/mobileNumber)))

However it now only evaluates the first <person> and returns nothing for the second. Any suggestions?

sammy88888888
  • 458
  • 1
  • 5
  • 18

1 Answers1

0

It is not possible for xpath queries to create nodes; xslt is used to create/transform xml. I suggest, that you use xpath to select all person nodes, then use javascript to iterate the child nodes of person. Within the iteration loop you can get the text of each node and at the same time test for the missing mobileNumber node is react accordingly.

Phil Blackburn
  • 1,047
  • 1
  • 8
  • 13
  • I don't want the xPath to create nodes, just return something where a node does not exist. – sammy88888888 Jul 24 '16 at 14:18
  • Your example xpath and the results suggest that you are working with a set of nodes. To expand on my initial sentence - xpath is used to select nodes from an existing xml document, it can not create nodes. Just like SQL SELECT selects rows from a db table but cannot insert rows. The reason why your second update doesn't work is because there is no mobileNumber node in the 2nd person to match against. You would need to add an empty mobileNumber under the 2nd person into the *source document* because like I say, xpath can not create a node. – Phil Blackburn Jul 24 '16 at 15:25
  • Yes but to use your SQL example you can do something like `WHERE NOT EXISTS` to highlight where data is not present. The example above works if you pass in the position of `` (e.g. `[1]` returns `5678` while `[2]` returns `null`. – sammy88888888 Jul 24 '16 at 15:36
  • When using mobileNumber[2] you're selecting a single node or a null(missing node) then concat() uses that value to return a single text result. If you only want a single value result, then you can do this but you want a set of nodes (as in the question) you cant have the xpath 'inject' a node where one does not exist. Lets not go off-topic with SQL but to clarify..WHERE NOT EXISTS does not create rows, it tests for non-existence and can be use to create a column but not a row. xml nodesets are like sql rowsets. I use sql as an example only to emphasise the point that xpath works on sets. – Phil Blackburn Jul 24 '16 at 16:35