Back

Explore Courses Blog Tutorials Interview Questions
0 votes
2 views
in DevOps and Agile by (19.7k points)

I'm trying to write my own expected condition. What I need... I have an iframe. and I also have an image in it. I want to continue processing when the image's screen will change. What I did:

class url_changed_condition(object):

    '''

    Checks whether url in iframe has changed or not

    '''

    def __init__(self, urls):

        self._current_url, self._new_url = urls

    def __call__(self, ignored):

        return self._current_url != self._new_url  

and later in the code I have:

def process_image(self, locator, current_url):

    try:

        WebDriverWait(self.driver, 10).until(ec.presence_of_element_located((By.TAG_NAME, u"iframe")))

        iframe = self.driver.find_element(*locator)

        if iframe:

            print "Iframe found!"

        self.driver.switch_to_frame(iframe)

        WebDriverWait(self.driver, 10).until(ec.presence_of_element_located((By.XPATH, u"//div")))

        # WebDriverWait(self.driver, 10).until(

            # url_changed_condition(

                # (current_url, self.driver.find_element(By.XPATH, u"//a/img").get_attribute(u"src"))))

        img_url = self.driver.find_element(By.XPATH, u"//a/img").get_attribute(u"src")

        print img_url

        self.search_dict[self._search_item].append(img_url)

        self.driver.switch_to_default_content()

    except NoSuchElementException as NSE:

        print "iframe not found! {0}".format(NSE.msg)

    except:

        print "something went wrong"

        import traceback

        import sys

        type_, value_, trace_ = sys.exc_info()

        print type_, value_

        print traceback.format_tb(trace_)

    finally:

        return current_url  

This code works but returns the same URL multiple times. The problem is when I uncomment url_changed_condition it falls with TimeoutException in
(current_url, self.driver.find_element(By.XPATH, u"//a/img").get_attribute(u"src"))
The line below it works fine... I don't get it.

1 Answer

0 votes
by (62.9k points)

It is actually pretty easy. First of all, what is a Custom Expected Condition in Python selenium bindings:

It is a new-style class (based on the object), it has __call__() magic method defined which returns a boolean. There is a big set of built-in expected condition classes. As you want to wait until an element's text will start with the desired text, take a look at this below example to understand how you be able to resolve your issue:

from selenium.webdriver.support import expected_conditions as EC

 

class wait_for_text_to_start_with(object):

    def __init__(self, locator, text_):

        self.locator = locator

        self.text = text_

 

    def __call__(self, driver):

        try:

            element_text = EC._find_element(driver, self.locator).text

            return element_text.startswith(self.text)

        except StaleElementReferenceException:

            return False

Usage:

 WebDriverWait(driver, 10).until(wait_for_text_to_start_with((By.ID, 'myid'), "Hello, World!"))

Browse Categories

...