Edit report at https://bugs.php.net/bug.php?id=62260&edit=1

 ID:                 62260
 User updated by:    yajo dot sk8 at gmail dot com
 Reported by:        yajo dot sk8 at gmail dot com
 Summary:            XPath does not search correctly in nodes with text
                     and other nodes
-Status:             Open
+Status:             Closed
 Type:               Bug
 Package:            *XML functions
 Operating System:   Linux
 PHP Version:        5.3.13
 Block user comment: N
 Private report:     N

 New Comment:

Salathe, thanks for the point, you are right.

Replacing the xquery by '//text()[contains(., "world")]/..' works perfectly.


Previous Comments:
------------------------------------------------------------------------
[2012-06-08 08:29:46] sala...@php.net

I may be wrong, but my understanding is as follows.

text() returns a list of node [1], whereas contains() expects two string 
arguments [2].  Because of this the list of 
text nodes is converted to a string, as with string():

"A node-set is converted to a string by returning the string-value of the node 
in the node-set that is first in 
document order. If the node-set is empty, an empty string is returned." [3]

[1] http://www.w3.org/TR/xpath/#path-abbrev
[2] http://www.w3.org/TR/xpath/#function-contains
[3] http://www.w3.org/TR/xpath/#function-string

------------------------------------------------------------------------
[2012-06-08 07:34:19] yajo dot sk8 at gmail dot com

Description:
------------
When a node has inner nodes and you want to search into its text value, only 
the first text node is selected.

This is wrong because, as http://www.w3.org/TR/xpath/#path-abbrev says:
> text() selects all text node children of the context node

Test script:
---------------
$xml = <<<END
<?xml version="1.0" encoding="UTF-8"?>
<root>
    <first>
        Hello
        <second>
            world
        </second>
        world
    </first>
</root>
END;

$doc = DOMDocument::loadXML($xml);
$xpath = new DOMXPath($doc);

foreach ($xpath->query('//*[contains(text(), "world")]') as $node)
    echo $node->nodeName . PHP_EOL;

Expected result:
----------------
first
second

Actual result:
--------------
second


------------------------------------------------------------------------



-- 
Edit this bug report at https://bugs.php.net/bug.php?id=62260&edit=1

Reply via email to