7

I have one element with attribute "aria-busy" that changes from true to false when data is in searching and done. How can I use selenium Expected Conditions and Explicit Waits to wait a default time like 20 seconds, if 20 seconds reaches and the attribute is not changed from true to false. throw exceptions. I have following, but it does not really work

import selenium.webdriver.support.ui as ui
from selenium.webdriver.support import expected_conditions as EC

<div id="xxx" role="combobox" aria-busy="false" /div>
class Ele:
    def __init__(self, driver, locator)
        self.wait = ui.WebDriverWait(driver, timeout=20)

    def waitEle(self):
        try:
            e = self.driver.find_element_by_xpath('//div[@id='xxxx']')
            self.wait.until(EC.element_selection_state_to_be((e.get_attribute('aria-busy'), 'true')))
        expect:
            raise Exception('wait timeout')

2 Answers 2

9

An Expected Condition is just a callable, you can define it as a simple function:

def not_busy(driver):
    try:
        element = driver.find_element_by_id("xxx")
    except NoSuchElementException:
        return False
    return element.get_attribute("aria-busy") == "false"

self.wait.until(not_busy)

A bit more generic and modular, though, would be to follow the style of the built-in Expected Conditions and create a class with a overriden __call__() magic method:

from selenium.webdriver.support import expected_conditions as EC

class wait_for_the_attribute_value(object):
    def __init__(self, locator, attribute, value):
        self.locator = locator
        self.attribute = attribute
        self.value = value

    def __call__(self, driver):
        try:
            element_attribute = EC._find_element(driver, self.locator).get_attribute(self.attribute)
            return element_attribute == self.value
        except StaleElementReferenceException:
            return False

Usage:

self.wait.until(wait_for_the_attribute_value((By.ID, "xxx"), "aria-busy", "false"))
Sign up to request clarification or add additional context in comments.

Comments

2

Another approach would involve checking the attribute value with a custom locator where you would not only check the id but also the aria-busy attribute value:

self.wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, "#xxx[aria-busy=false]")))

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.