SugarOnBacon
SugarOnBacon

Reputation: 115

Check for temporary element with Capybara

An element appears briefly after a click and then disappears after the server returns a response. This is the current code:

#send request to server
something.click
#make sure temporary element appears
expect(page).to have_css('#foo')
#make sure temporary element disappears after server returns response
expect(page).to have_no_css('#foo')

Sometimes the element will disappear so fast, that the first expect does not recognise its existence and the test fails. However, if the first expect is removed, the second expect might be executed before the element first appears and we do not successfully test for non-existence.

Is there a better way to test for briefly appearing elements in Capybara?

Edit: It would be enough to test that the element has disappeared, but considering that sleep should not be used with Capybara.

Upvotes: 1

Views: 248

Answers (1)

Thomas Walpole
Thomas Walpole

Reputation: 49950

The asynchronous nature of browser testing means that it's not always possible to reliably locate temporary elements with a default setup. Since you state you're ok with just making sure the element has disappeared, and you have a timeframe you can reliably guarantee the element would have appeared in you could do something like

#send request to server
something.click
#wait for temporary element to appear - don't error if it doesn't
page.has_css?('#foo', wait: 2)
#make sure temporary element disappears after server returns response
expect(page).to have_no_css('#foo')

That will wait up to 2 seconds (adjust as needed) for the element to appear. If it does appear it will continue as soon as the element is visible, if not it will return false after 2 seconds and continue on.

If it is actually required to detect the appearing and disappearing of the element, then any solution would depend on what exactly triggers the display and removal of the element. Assuming it's an indicator of a request happening which appears when the request starts and then is removed on request completion you would need to look at slowing down the request so the element remains visible longer. Two ways that could be accomplished would be

  1. A programmable proxy like puffing-billy
  2. If using the Selenium driver with Chrome you could use page.driver.browser.set_network_conditions although this would be a driver specific solution.

Upvotes: 2

Related Questions