Python seleniumium WebDriver. Ich schreibe meinen eigenen Zustand

Ich versuche, meinen eigenen erwarteten Zustand zu schreiben. Was ich brauche … Ich habe einen Iframe. und ich habe auch ein Bild darin. Ich möchte die Verarbeitung fortsetzen, wenn sich der Bild-Scr ändert. Was ich getan habe:

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 

und später im Code habe ich:

 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 

Dieser Code funktioniert, gibt aber dieselbe URL mehrmals zurück. Das Problem ist, wenn ich url_changed_condition , fällt es mit TimeoutException in
(current_url, self.driver.find_element(By.XPATH, u"//a/img").get_attribute(u"src"))
Die Linie darunter funktioniert gut … Ich verstehe es nicht.

Solutions Collecting From Web of "Python seleniumium WebDriver. Ich schreibe meinen eigenen Zustand"

In diesem Thema fehlt ein Beispiel für eine benutzerdefinierte erwartete Bedingung .

Es ist eigentlich ziemlich einfach. Was ist ein erwarteter Zustand in Python-seleniumbindungen?

  • es ist eine neue class (basierend auf object )
  • Es hat __call__() magische Methode definiert, die einen booleschen __call__() zurückgibt

Es gibt eine große Menge von integrierten erwarteten Zustandsklassen .

Lassen Sie uns ein Beispiel durcharbeiten. Nehmen wir an, wir möchten warten, bis der Text eines Elements mit einem gewünschten Text beginnt :

 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 

Verwendung:

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

Laut der Dokumentation :

WebDriverWait ruft die ExpectedCondition standardmäßig alle 500 Millisekunden auf, bis sie erfolgreich zurückgegeben wird. Eine erfolgreiche Rückgabe ist für den ExpectedCondition-Typ Boolean return true oder nicht null return value für alle anderen ExpectedCondition-Typen.

Die Tatsache, dass Sie dieselbe URL mehrfach erhalten, wenn Sie die benutzerdefinierte Wartezeit auskommentieren, sollte Ihnen einen Hinweis geben.

In __call__() Sie immer False da sich die URLs nie ändern. Da Sie False , wird die ExpectedCondition nie erfüllt und Sie erhalten die TimeoutException .

Definieren Sie die Logik von ExpectedCondition entweder neu, oder testen Sie sie für einen anderen Fall.

Mit der von @alecxe beschriebenen Technik, aber leicht modifiziert, um mit den expected_conditions fertig zu werden, die ein Element anstelle eines Locators akzeptieren: (In diesem Fall, da es kein selenium.webdriver.support.expected_conditions.invisibility_of(element) , bin ich Warten auf die is_displayed() Methode, um False zu signalisieren)

 class wait_for_element_to_be_invisible(object): def __init__(self, element): self.element = element def __call__(self, driver): return not(self.element.is_displayed()) def test_collapsible_blocks_expand_or_collapse(self): self.browser.get(self.server_url+'/courses/1/') shadables = self.browser.find_elements_by_class_name('shade') for shadable in shadables: ## parent, then sibling element (*) shady_bit = shadable.find_element_by_xpath('../following-sibling::*') element = WebDriverWait(self.browser, 10).until( EC.visibility_of(shady_bit)) shadable.click() element = WebDriverWait(self.browser, 10).until( self.wait_for_element_to_be_invisible(shady_bit)) 

Das HTML-Fragment mit den relevanten Bits des DOM ist:

 

Title of Section

Descriptive part which is shadable

`