• visibility_of_element_located源码解析


    看WebDriverWait(self.driver, wait_time).until(EC.visibility_of_element_located((by, locator)))源码的时候,不太明白visibility_of_element_located((by, locator))内为什么是两层括号,因为源码是这样写的:

    class visibility_of_element_located(object):
        """ An expectation for checking that an element is present on the DOM of a
        page and visible. Visibility means that the element is not only displayed
        but also has a height and width that is greater than 0.
        locator - used to find the element
        returns the WebElement once it is located and visible
        """
        def __init__(self, locator):
            self.locator = locator
    
        def __call__(self, driver):
            try:
                return _element_if_visible(_find_element(driver, self.locator))
            except StaleElementReferenceException:
                return False
    

      

       

    __call__()的作用是,让实例对象也像函数一样作为可调用对象来使用,正常来讲visibility_of_element_located(locator)(driver)才对,直到看了下until的源码,才发现有这一层:value = method(self._driver),其中这个method就是EC.visibility_of_element_located((by, locator))实例对象,method(self._driver)就是EC.visibility_of_element_located((by, locator))(self._driver),也就是把实例对象作为参数一样传了个参数,self._driver。其实前者((by, locator))是__init__()做初始化,只不过参数是个元组(by, locator),这个元组作为实例对象的属性self.locator,而后者(self._driver)就是__call__()的作用

    def until(self, method, message=''):
            """Calls the method provided with the driver as an argument until the 
            return value is not False."""
            screen = None
            stacktrace = None
    
            end_time = time.time() + self._timeout
            while True:
                try:
                    value = method(self._driver)
                    if value:
                        return value
                except self._ignored_exceptions as exc:
                    screen = getattr(exc, 'screen', None)
                    stacktrace = getattr(exc, 'stacktrace', None)
                time.sleep(self._poll)
                if time.time() > end_time:
                    break
            raise TimeoutException(message, screen, stacktrace)
    

      

    当使用EC.visibility_of_element_located((by, locator))(self._driver)时,总共进行了以下的步骤:

    1. 实例化一个EC.visibility_of_element_located,传入参数(by, locator),将其赋值给属性self.locator

    2. 通过__call__(),将参数self._driver(实际上这个self.driver就是WebDriverWait中的self.driver传进来的)和self.locator传给内层方法_find_element()

      2.1 这个find_element(self._driver, self.locator)对应着源码中的driver和by,再通过*by解包(by, locator),使其这样调用driver.find_element(by, locator)

    def _find_element(driver, by):
        """Looks up an element. Logs and re-raises ``WebDriverException``
        if thrown."""
        try:
            return driver.find_element(*by)
        except NoSuchElementException as e:
            raise e
        except WebDriverException as e:
            raise e
    

      

     

      2.2 然后driver.find_element(by, locator)找到元素对象并返回给_find_element()方法

      2.3 _find_element()方法拿到元素对象,此时作为参数传递给_element_if_visisble()方法,element_if_visisble()方法通过判断元素是否可见,返回True或False

    until作为一个判断条件,来决定是否继续寻找可见元素,主要有这几种情况:如果EC.visibility_of_element_located((by, locator))(self._driver)返回为True,则返回对应的True;如果已超时,则抛出超时异常

     
    努力努力努力
  • 相关阅读:
    [java核心篇02]__内部类
    iOS学习之MVC,MVVM,MVP模式优缺点
    iOS MVC、MVP和MVVM理解
    网络常见的9大命令
    计算机网络基础知识总结
    iOS面试常见问题和知识点汇总
    NSMutableArray 删除可变数组元素
    iOS之集成GoogleMap定位、搜索注意事项
    iOS 13-Sign In with Apple
    Lipo移除ORC架构
  • 原文地址:https://www.cnblogs.com/wwtest/p/14081584.html
Copyright © 2020-2023  润新知