Reputation: 149
I am trying to select the div
tags that contain "month-table_col"
(select by month).
...
<div class="month-table">
<div class="month-table_row">
<div class="month-table_col">Jan</div>
<div class="month-table_col">Feb</div>
<div class="month-table_col">Mar</div>
</div>
<div class="month-table_row">
<div class="month-table_col">Apr</div>
<div class="month-table_col">May</div>
<div class="month-table_col">Jun</div>
</div>
<div class="month-table_row">
<div class="month-table_col">Jul</div>
<div class="month-table_col">Aug</div>
<div class="month-table_col">Sep</div>
</div>
<div class="month-table_row">
<div class="month-table_col">Oct</div>
<div class="month-table_col">Nov</div>
<div class="month-table_col">Dec</div>
</div>
</div>
...
Here is the XPath code used to specify the div
tags, for example, to select the div
tag which has November value.
//div[contains(@class, 'month-table_col') and contains(text(), 'Nov')]
After running the below command in Google Chrome console,
$x("//div[contains(@class, 'month-table_col') and contains(text(), 'Nov')]")
The result: it returns an array of one element like this
[div.month-table_col]
0: div.month-table_col
lastIndex:(...)
lastItem:(...)
length: 1
__proto__:Array(0)
Even if I tried specifying the index of 1, it returns the same result as shown above.
$x("//div[contains(@class, 'month-table_col') and contains(text(), 'Nov')][1]")
The returned result is correct, but if there is anyway that I can get the element as a tag, not the array result.
Expected result:
<div class="month-table_col">Nov</div>
Upvotes: 2
Views: 1251
Reputation: 163468
Firstly, I think you haven't understood what contains() does in XPath. I think you want @class = 'month-table_col'
rather than contains(@class, 'month-table_col')
- contains() searches for a matching substring. Similarly, contains(text(), 'Nov')
should probably be simply .='Nov'
. (Always better to compare the string value of the element rather than looking for child text nodes if you can).
But that's not your problem: your problem is the operator precedence of '//' versus '[]'. The expression //A[1]
means "for every node in the document, select its first A
child element if it has one". You want (//A)[1]
which applies the [1]
predicate to the final result, not to each child::A
selection individually.
Upvotes: 2
Reputation: 111696
The Chrome DevTools XPath console function, $x()
, always returns an array, even if there's a single node that was selected, and even if there were no nodes selected.
You can then use JavaScript indexing to extract any given array element. If the result of your XPath was a single node, then append [0]
to get that node from within the returned array:
$x("//div[contains(@class, 'month-table_col') and contains(text(), 'Nov')]")[0]
Reminder: XPath node sets and sequences are 1-based; JavaScript arrays are 0-based.
Upvotes: 2