Q: When is a button not a button?
A: When it is a YUI button
Selenium, at its core, deals with HTML things stored in the DOM. And
does a pretty good job at it. But things start to get confusing when the
people creating the page start to get fancy and use third-party widgets
like those provided by YUI. This post is about how
to fake your way through Se automation when you encounter YUI controls,
specifically a YUI Button.
The big thing to understand is that YUI buttons are not buttons (to the
browser), they are in fact just blobs of JS that happen to look like a
button. When you ‘click’ on one, a callback is fired to execute another
bit of JS to make it look like you click did something. Ahhh, AJAXy
goodness.
But because there is nothing happening at the DOM level, we need to
simulate both the ‘click’ and the subsequent action. For example, here
is a helper function I wrote to deal with a ‘checkbox’ type YUI button
for a client.
if se.is_element_present("//span[@id='PinBalloonSelector']"):
se.get_eval("window.ShowBalloonButton.set('checked', true)")
se.get_eval("window.PersistBalloonPinMode()")
se.wait_for_condition("selenium.isElementPresent(\"//div[@id='balloonContentDiv']/div\")", "60000")
Important things to note:
- YUI buttons are children of the window object so start your hunt there
- To ‘click’ the box on you set the attribute ‘checked’ to true. Setting to false ‘unclicks’ it
- After the click you need to call the JS function that would normally be triggered as we’re sneaking operations in under-the-hood
- Because all of this is happening in JS, you need to use the get_eval variant that your binding provides
That took me well over a day to figure out, so I figure someone else has
likely run into issues where Se-IDE has recorded a button interaction
one way but on playback or export it didn’t work because the button
isn’t an HTML button, it is a YUI button.