Optimizing XPath queries

70 views
Skip to first unread message

Aditya Ivaturi

unread,
Jan 12, 2010, 2:50:46 PM1/12/10
to Selenium Users
My query is based on this discussion here:
http://groups.google.com/group/comp.lang.javascript/browse_thread/thread/a59ce20639c74ba1/a9d9f53e88e5ebb5

We run quite a bit of XPath queries & even though it is fairly fast
enough in Firefox, I think the way XPath expressions are "queried" in
Selenium can be improved. For example, in some of the pages, we "list"
the data in a specific table format: //table[@class='tblList'] would
get you all those specific tables on a single page. So if I wanted to
find some thing in the second table on that page, I'd try //table
[@class='tblList'][2] & so on.

Now, here is where you can optimize your queries. If I wanted to say
grab all the data in those tables & dump it out as a hash. Then I'd go
through each table cell & get the relevant data. But in doing so I
always end up using // query that means I always try to evaluate at
the root of the document. Instead it'd be faster if I can do something
similar as in the above Google groups discussion - i.e. I already know
my first table is //table[@class='tblList'][1]. So is there any way to
grab that node in selenium & "continue" my XPath using relative
syntax like ./tbody/tr[1]/td[1]/text(). Note the period at the
beginning of that query, which states that find the relevant text in
the table cell of the first table.

I couldn't find a way to do it but I believe this should speed up the
overall processing of queries, if you do a lot of XPath evaluation on
a given document.

David Burns

unread,
Jan 13, 2010, 4:25:36 AM1/13/10
to Selenium Users
You can use CSS locators to find what you are after.

E.g.

xpath=//table[@class='tblList'][1] would be CSS=table.tblList

XPath isn't native in Internet Explorer but CSS locators are so will
be a lot quicker

David Burns
http://www.theautomatedtester.co.uk/

On Jan 12, 7:50 pm, Aditya Ivaturi <ivat...@gmail.com> wrote:
> My query is based on this discussion here:http://groups.google.com/group/comp.lang.javascript/browse_thread/thr...

Aditya Ivaturi

unread,
Jan 13, 2010, 5:51:57 PM1/13/10
to Selenium Users

> You can use CSS locators to find what you are after.
>

CSS locators are not as powerful as XPath. Obviously, I have omitted
some information in my original post. In this case for e.g., a single
page can have multiple tables of class 'tblList'. So in XPath, I can
say //table[@class='tblList'][1] to get me the first table that
matches my condition. But in case of CSS locators it is simply not
possible - at least using the CSS locators specification. The closest
you can come to is using some thing like table.tblList:nth-child(1),
but that will work if this table element is the first child of its
parent node. If you have any other element taking up the table's place
- that condition will fail. For e.g. if I have a couple of <br/>
elements before this particular table element, then this table is the
3rd child of its parent node.

Bottom line, I think XPath is a more programmer friendly & powerful
locator scheme. But the biggest hurdle is the stupid IE with its lame
JS engine and absolutely no support for XPath. Firefox had it since
1.0.

Regardless, I did find the answer to my original question & the answer
is no - there is no support for context nodes in Selenium since
Selenium never returns an element reference back to the client. It is
apparently possible in WebDriver though, but then I have to wait till
2.0 comes out.

Santiago Suarez Ordoñez

unread,
Jan 14, 2010, 10:53:57 PM1/14/10
to seleniu...@googlegroups.com
So in XPath, I can
say //table[@class='tblList'][1] to get me the first table that
matches my condition. But in case of CSS locators it is simply not
possible - at least using the CSS locators specification. The closest
you can come to is using some thing like table.tblList:nth-child(1),
but that will work if this table element is the first child of its
parent node. If you have any other element taking up the table's place
- that condition will fail. For e.g. if I have a couple of <br/>
elements before this particular table element, then this table is the
3rd child of its parent node.
 
Bottom line, I think XPath is a more programmer friendly & powerful
locator scheme. But the biggest hurdle is the stupid IE with its lame
JS engine and absolutely no support for XPath. Firefox had it since
1.0.
I'd just say: the best tool is the one that gets the job done easier, and in most cases, I was able to do it using css in a better performant cleaner way.
The only locators I coudn't replace with CSS is the ones that do reverse navigation, for example:

//table/tr[td[input[@value="cell to detect"]]]/td/input[@class="input-in-another-cell-from-the-row"]
 
Hope it helps,
Santi

Aditya Ivaturi

unread,
Jan 15, 2010, 2:48:17 PM1/15/10
to Selenium Users

I did look at that when I was experimenting with CSS selectors, but I
don't think you can use "filters" with nth-of-type. For e.g. in the
example I provided I cannot do table.tblList:nth-of-type(1). As far as
I know the only way to use it is table:nth-of-type(1). If I am missing
something, please do let us know.

Santiago Suarez Ordoñez

unread,
Jan 17, 2010, 1:06:28 PM1/17/10
to seleniu...@googlegroups.com
On Fri, Jan 15, 2010 at 5:48 PM, Aditya Ivaturi <iva...@gmail.com> wrote:
I did look at that when I was experimenting with CSS selectors, but I
don't think you can use "filters" with nth-of-type. For e.g. in the
example I provided I cannot do table.tblList:nth-of-type(1). As far as
I know the only way to use it is table:nth-of-type(1). If I am missing
something, please do let us know.

I don't see a reason for which that wouldn't work. Actually, the first example in the pseudo-classes documentation is an element with class and pseudo-class defined:
http://www.w3.org/TR/2005/WD-css3-selectors-20051215/#pseudo-classes

Santi

Aditya Ivaturi

unread,
Jan 18, 2010, 5:11:15 PM1/18/10
to Selenium Users

>
> I don't see a reason for which that wouldn't work. Actually, the first
> example in the pseudo-classes documentation is an element with class and
> pseudo-class defined:http://www.w3.org/TR/2005/WD-css3-selectors-20051215/#pseudo-classes
>

I'm using Firefinder (an addon to firebug) to evaluate those CSS
queries & whenever I use filters with nth-of-type() it never returned
any resutls. So I tried it with CSSQuery (which is the javascript
library that Selenium uses) & the result was the same. May be I am
missing something? Can you try installing Firefinder in your FF
browser & see if you can use filters on the nth-of-type() & get
results back?

Santiago Suarez Ordoñez

unread,
Jan 18, 2010, 11:25:39 PM1/18/10
to seleniu...@googlegroups.com
I'm packed this week. I'll add it to my TODO list and will let you know once I have a test working with that kind of locator.

Best,
Santi


--
You received this message because you are subscribed to the Google Groups "Selenium Users" group.
To post to this group, send email to seleniu...@googlegroups.com.
To unsubscribe from this group, send email to selenium-user...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/selenium-users?hl=en.




Reply all
Reply to author
Forward
0 new messages