It turns out this is a common problem and is due to the lack for native xpath support in IE. So for all the selenium tests that use xpath=//..... in IE the xpath is actually being evaluated using javascript ... ouch. An alternative is to use css locators, you can't do this everywhere but as well as improving the IE performance it can also provide some rather tidy rules. For example
xpath=//div[contains(@class,'balance')]
or
css=.balance
xpath=//div[@id,'topLeft')//span[contains(@class,'name')]
or
css=#topLeft .name
So even if you dont' care about IE using css selectors might be a lot nicer. (It might also improve your css skills!)
7 comments:
This is really great. The only problem I've had trying to use it is when selecting a particular element from a set that match the rule (e.g. dealing with list items or table rows when you're trying to target a particular one). Nothing is more horrible to maintain or more prone to break due to minor front end changes than overcomplex XPath locators.
Targetting table elements using verifyTable is a similarly powerful technique.
It's worth noting that you can still use (verify|waitFor)Attribute with css selectors. e.g.
verifyAttribute #someContainer a.someLinkClass@href http://icanhascheezburger.com/
Ah, cool. I didn't realise you could access attributes like that.
It's also worth noting that the examples given are not entirely comparing apples with pears.
Take this XPath:
xpath=//div[contains(@class,'balance')]
If the reason behind the 'div' is actually to confirm that the element is a DIV, then this would be the correct CSS locator syntax:
css=div.balance
Although having said that, the 'contains' function of the XPath engine would also match substrings of class names, so a DIV with a class of 'unbalanced' would match the XPath rule but not the CSS rule.
If you want to do explicit class name matching with an XPath, one way (there are probably many) would be:
xpath=//div[contains(concat(' ', @class, ' '), ' balance ')]
Dan that's a really good point that I hadn't really thought about before. Thanks for the heads up it will keep me from making a bonehead mistake in the future.
I also managed to get specific element selection working with
css=#someContainer p:nth-child(2)
I can't remember whether we tried this with IE and found it didn't work, however it seems to work with firefox.
It's not quite as clean as you might like but I've found it usually looks better than the equvalent xpath.
One more reason to encourage css rather than xpath locators is that working with css locators will also help your css work, whereas xpath locators are only good for writing selenium tests (or parsing xml documents ... shudder),
Post a Comment