zoukankan      html  css  js  c++  java
  • selenium与页面的交互

    学习准备:

      1、下面的方法都是用 Python3 语言编写的,所以要准备:Python3 语言基础

      2、如果要实践下面的方法,请看我的随笔:Python3+Selenium+PyCharm 运行环境

      3、还要了解一下简单的元素定位,我的随笔 :Selenium 元素定位

      由于本人水平有限,以下有些 代码 和 HTML示例 省略,还请见谅!有错的地方请留言指点!

    一、WebDriver 浏览器的属性

      WebDriver 提供了很多属性来支持对浏览器的操作,例如,获取测试地址、多窗口的处理、获取浏览器的名称等。

    1、获取测试的地址

      方法:current_url

    from selenium import webdriver
    
    driver = webdriver.Firefox()
    driver.maximize_window()
    driver.get('http://www.baidu.com/')
    driver.implicitly_wait(30)
    print('测试地址为:{0}'.format(driver.current_url))
    driver.quit()
    

    2、获取当前页面代码

      方法:page_source

    print('页面代码如下:{0}'.format(driver.page_source))
    

    3、获取当前 Title

      方法:title

    print('当前的Title为:{0}'.format(driver.title))
    

    4、页面的前进和后退

      方法:前进用到的方法是 forward,后退用到的方法是 back

    from selenium import webdriver
    import time as t
    driver = webdriver.Firefox()
    driver.maximize_window()
    driver.get('http://www.baidu.com/')
    t.sleep(2)
    driver.get('http://www.bing.com')
    t.sleep(2)
    #返回到百度
    driver.back()
    print('当前URL为:{0}'.format(driver.current_url))
    t.sleep(2)
    #前进到bing
    driver.forward()
    print('当前URL为:{0}'.format(driver.current_url))
    driver.quit()
    

    5、关闭程序

      在 selenium 中,quit 方法用来退出驱动程序(Driver)并关闭执行的浏览器;而 close 方法用来关闭执行的浏览器,所以关闭程序建议使用 quit 方法。

    6、加载测试地址

      在 UI 自动化测试中,打开测试地址用到的方法是 get 方法,它的参数是要打开的测试页面的地址。

    driver.get('http://mail.sina.com.cn/')
    

    7、多窗口实践

      窗口处理的方法,current_window_handle 用来获取当前浏览器的窗口句柄,window_handles 用来获取浏览器的所有窗口句柄。如下,实现在新浪登录页面点击注册,在注册页面邮箱地址输入框中输入邮箱地址,再次跳转到登录页面。

    from selenium import webdriver
    import time
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.get('http://mail.sina.com.cn/')
    #获取当前窗口句柄
    now_handle = driver.current_window_handle
    time.sleep(1)
    #点击注册链接
    driver.find_element_by_link_text('注册').click()
    time.sleep(1)
    #获取所有窗口句柄
    handles  = driver.window_handles
    #对所有窗口句柄循环处理
    for handle in handles:
        if handle != now_handle:
            #窗口变化之后需要定位当前窗口
            driver.switch_to.window(handle)
            time.sleep(2)
            driver.find_element_by_name('email').send_keys('bing')
            time.sleep(2)
            #关闭注册页面
            driver.close()
    driver.switch_to.window(now_handle)
    time.sleep(2)
    #在账号输入框输入邮箱
    driver.find_element_by_id('freename').send_keys('bing')
    time.sleep(2)
    
    driver.quit()
    

    8、浏览器最大化

      方法:maximize_window,一般打开浏览器时,界面并不是最大化的,这对 UI 自动化测试的影响比较大,所以建议使用此方法让浏览器最大化。

    driver.maximize_window()
    

    9、刷新

      方法:refresh ,有些场景要用到页面刷新后查看效果。

    driver.refresh()
    

    10、获取执行的浏览器

      方法:name

    print('测试执行的浏览器为:{0}'.format(driver.name))

    二、WebElement 类的方法

    1、清除

      方法:clear

    em = driver.find_element_by_name('email')
    #输入关键字
    em.send_keys('selenium')
    time.sleep(2)
    #清除关键字
    em.clear()
    

    2、获取元素属性值

      方法:get_attribute,在测试中,经常需要获取输入框中的值,或者获取输入框中的提示信息。

      如,“请输入用户名”的元素属性是 place,获取提示信息。

    name = driver.find_element_by_name('username')
    print('用户名输入框中提示信息为:{0}'.format(name.get_attribute('place')))
    

      在输入框中输入的值一般都在 value 属性中,如在百度搜索输入框中输入的搜索关键存放在百度搜索 input 的 value 属性中。

    sr = driver.find_element_by_id('kw')
    sr.send_keys('selenium')
    print('填写的关键字为:{0}'.format(sr.get_attribute('place')))
    

    3、检查元素是否可见

      方法:is_displayed,用于测试该属性对用户是否可见,返回结果为布尔类型(True、False)。

    about = driver.find_element_by_partial_link_text('关于百度')
    print('关于百度是否可见:{0}'.format(about.is_displayed()))
    

    4、检查元素是否可编辑

      方法:is_enabled,用于测试文本是否可编辑,返回结果是布尔类型。

    sr = driver.find_element_by_id('kw')
    print('搜索输入框是否可编辑:{0}'.format(sr.is_enabled()))
    

    5、检查是否已选中

      方法:is_selected,主要针对单选按钮或复选按钮,判断它们是否选中,返回结果是布尔类型。

    zd = driver.find_element_by_id('st1')
    print('自动登录是否默认选中:{0}'.format(zd.is_selected()))
    

    6、提交表单

      方法:submit,在 form 表单中,点击“提交”按钮,跳转到另一个页面。click 只是单纯的点击;submit 一般是有 form 表中,只是用在有 form 表单的提交。

      form 表单的 HTML 代码中有:

    <form action="index.html" method="get">
        <p>
            昵称:<input type="text" name="username">
        </p>
        <p>
            <input type="submit" name="form" value="提交">
        </P>
    </form>
    

      点击“提交”按钮跳转到 index.html 页面,实现交互的主要代码:

    driver.find_element_by_name('username').send_keys('user0')
    driver.find_element_by_name('form').submit()
    

     三、下拉框实战

    1、Select 类的详解

      针对自动化中的下拉框,selenium 中提供了 select 类来处理,在 select 模块中导入方式是:from selenium.webdriver.support.select import Select 。

    2、定位思路

      在百度搜索设置中设置期望的搜索结果显示的条数为例,这部分的HTML 代码如下:

    <td id="se-setting-3">
        <select name="NR" id="nr">
            <option value="10" selected="">每页显示10条</option>
            <option value="20">每页显示20条</option>
            <option value="50">每页显示50条</option>
        </select> 
        百度的原始设定10条最有效且快速
    </td>
    

      实现步骤:

      1)首先定位到 Select 下拉框的元素属性,具体代码:nr = driver.find_element_by_name('NR');

      2)实例化 Select 类,参数为 nr,具体代码:select = Select(nr);

      3)Select 实例化后的对象 select 可以调用 Select 类的任何一个方法。

    3、在 Select 类中的各种定位实践

      方法1:select_by_index,参数是索引值,如实现每页显示 50 条,索引是 2;

      方法2:select_by_value,本例子中的 value 值是 10、20、50;

      方法3:select_by_visible_text,文本信息就显而易见了吧,注意空格等,最好复制文本信息保持一致,具体代码如下。

    from selenium import webdriver
    from selenium.webdriver.support.select import Select
    from selenium.webdriver.common.action_chains import ActionChains as AC
    import time as t
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('http://www.baidu.com')
    
    #实现鼠标悬浮在百度首页的设置
    #这里为a 的第8个元素
    element = driver.find_element_by_css_selector('a.pf:nth-child(8)')
    t.sleep(3)
    AC(driver).move_to_element(element).perform()
    t.sleep(3)
    #点击设置中的搜索设置按钮
    driver.find_element_by_link_text('搜索设置').click()
    #driver.find_element_by_css_selector('.setpref').click()#没有成功
    t.sleep(2)
    #定位到下拉框元素属性
    nr = driver.find_element_by_name('NR')
    #实例化 Select 类
    select = Select(nr)
    select.select_by_index(2) # 索引定位
    # select.select_by_value('50') # value 定位
    # select.select_by_visible_text('每页显示20条') # 文本定位
    print('下拉框选择的最新条数是:',nr.get_attribute('value'))
    t.sleep(2)
    driver.quit()

    四、弹出框实践

    1、Alert 类的详解

      在HTML 的 Javascript 交互中主要有 Alert 警告框、Confirm 确认框、Prompt 消息对话框。

      在 Selenium 中对于弹出框的处理方法可以使用 alert 模块中的 Alert 类,在 Alert 类中,方法 text 用来获取 Alert 弹出框的文本信息。accept 和 dismiss 方法主要应用在 Confirm 弹出确认框中,accept 用来接受确认框,dismiss 用来拒绝确认框。send_keys 主要应用在 Prompt 消息对话框中,在输入框中输入要输入的值。在 Selenium 中是通过 switch_to_alert 方法调用 Alert 类中的方法,而 switch_to_alert 方法是属于 WebDriver 类的方法。

    2、警告框的处理

      如在百度搜索设置中,设置后点击“保存设置”按钮,弹出 alert 对话框,点击“确认”按钮。

    from selenium import webdriver
    from selenium.webdriver.support.select import Select
    from selenium.webdriver.common.action_chains import ActionChains as AC
    import time as t
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('http://www.baidu.com')
    
    #实现鼠标悬浮在百度首页的设置
    element = driver.find_element_by_css_selector('a.pf:nth-child(8)')
    t.sleep(3)
    AC(driver).move_to_element(element).perform()
    t.sleep(3)
    #点击设置中的搜索设置按钮
    driver.find_element_by_link_text('搜索设置').click()
    #driver.find_element_by_css_selector('.setpref').click()#没有成功
    t.sleep(2)
    #点击搜索设置按钮
    driver.find_element_by_css_selector('#gxszButton > a.prefpanelgo').click()
    t.sleep(2)
    #获取弹出框的文本信息
    print('alert 弹出文本信息为:{0}'.format(driver.switch_to.alert.text))
    #点击弹出框确认
    driver.switch_to.alert.accept()
    

      运行代码后,会打印出 Alert 的文本信息。

    3、确认框的处理

      Confirm 是弹出确认的对话框,可以选择“确认”或“取消”按钮,确认的方法是 accept;取消的方法是 dismiss。

    driver.switch_to.alert.accept()  #确认
    driver.switch_to.alert.dismiss() #取消
    

    4、消息对话框的处理

      Prompt 消息对话框,在 JavaScript 中用于询问一些需要与用户交互的信息,方法:send_keys。

    #在弹出输入框中输入
    driver.switch_to.alert.send_keys('python 学习')
    

     五、WebDriverWait 类实战

      在 UI 自动化测试中,首先要保障测试脚本的稳定运行。在实际的测试场景里,由于网络的因素导致需要测试的页面打不开或者打开延迟,从而导致页面元素找不到等各种错误的出现。

      等待方式主要存在以下三种方式:

      1)固定等待。如调用 time 模块中的 sleep 方法,固定等待几秒。

      2)隐式等待。用到的方法是 implicitly_wait,隐式等待指设置最长的等待时间。

      3)显示等待。主要是指程序会每隔一段时间执行自定义的程序判断条件,如果判断条件成功,程序就会继续执行;如果判断条件失败,程序就会报 TimeOutEcpection 的异常信息。

      time.sleep(3) 增加了固定等待 3 秒时间,如果每个步骤都增加固定等待时间,那么一个测试用例执行下来等待时间将会增加十几秒,大大地延长了测试用例的执行的时间。因此,在 Selenium 中提供了 WebDriverWait 类,专门解决网络延迟等待等问题。

    1、WebDriverWait 类详解

      WebDriverWait 类放置在 wait 模块在,使用该类时,需要先导入并且对它进行实例化,导入的代码如下:

    from selenium.webdriver.support.ui import WebDriverWait
    

      WebDriverWait 类的参数分别是 driver 和 timeout 。driver 指的是 webdriver 实例化后的对象,timeout 指的是具体的等待时间。WebDriverWait 类的 until 方法中,参数 method 指的是需要调用的方法,调用方法来自 expected_conditions 模块中的类,也就是说 WebDriverWait 会与 expected_conditions 模块结合起来应用。

      调用 expected_conditions 模块中的类后,一般返回两种形式的对象实例:一种是布尔型,返回 True 程序会继续执行,否则程序会报 TimeOutEcpection 的异常信息;另一种是返回某个具体实例对象,使用该对象就可以直接调用该类中的方法。

    2、元素可以见并且可操作

      element_to_be_clickable 判断某元素可见后执行输入、点击等操作。判断满足条件后返回的是 WebElement 类的实例对象,这样就可以调用 WebElement 类中的 send_keys 等方法。如下,实现点击百度首页的“百度一下”按钮,首先加载搜索的输入框,然后在输入框输入关键字,否则就返回错误的信息:

    from selenium import webdriver
    from selenium.webdriver.support.ui import WebDriverWait
    from selenium.webdriver.support import expected_conditions
    from selenium.webdriver.common.by import By
    import time as t
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('http://www.baidu.com')
    driver.implicitly_wait(30)
    '''
    WebDriverWait直接调用静态方法until,并且显示等待10s,
    在until的方法中又调用了expected_conditions,
    模块中的element_to_be_clickable类,
    在element_to_be_clickable类中需要指定按ID或者其他元素属性来指定元素属性。
    '''
    so = WebDriverWait(driver,10).until(expected_conditions.element_to_be_clickable((By.ID,'kw')))
    so.send_keys('Selenium')
    t.sleep(3)
    driver.quit()
    

      如果对以上代码中,故意写错元素属性,把 kw 写成 kww,执行后,则会有 TimeOutEcpection 的错误提示。

    3、指定元素的文本位置

      text_to_be_present_in_element 指定元素文本的位置,一般用于验证一个文本信息或者错误的提示信息,返回的是布尔型,可以打印出来看结果。

    disText = WebDriverWait(driver,10).until(expected_conditions.
              text_to_be_present_in_element((By.
              XPATH,'输入具体的xpath'),'需要验证的文本信息'))
    print('结果是:{0}'.format(disText))

    4、判断元素是否可见

      visibility_of_element_located 方法的作用是等元素可见后再执行操作。如下,百度首页的“关于百度”的链接:

    WebDriverWait(driver,10).until(expected_conditions.
        visibility_of_element_located(By.LINK_TEXT,'关于百度'))
    

     六、ActionChains 类实践

      在功能自动化测试中,经常会用到鼠标事件。在 Selenium 中,主要在 action_chains 模块的 ActionChains 类中,导入方式为:

    from selenium.webdriver.common.action_chains import ActionChains
    

    1、ActionChains 类详解

      在 ActionChains 类中提供了常用的鼠标操作方法,首先要对 ActionChains 类进行实例化,该类的构造函数参数为 driver,也就是 WebDriver 实例化后的对象,实例化后就可以调用它里面的方法了:

    from selenium import webdriver
    from selenium.webdriver.common.action_chains import ActionChains as AC
    import time as t
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('http://www.baidu.com')
    #对 AC 类进行实例化
    actionChains = AC(driver)
    #actionChains.   #这里就会显示该类的方法了
    driver.quit()
    

    2、鼠标悬浮操作

      move_to_element 方法用来使鼠标悬浮到某一元素上,以百度首页的搜索设置为例:

    #对 AC 类进行实例化
    actionChains = AC(driver)
    #实现鼠标悬浮在百度首页的设置
    element = driver.find_element_by_css_selector('a.pf:nth-child(8)')
    t.sleep(3)
    #鼠标悬浮到“设置”
    actionChains.move_to_element(element).perform()
    #点击设置中的搜索设置按钮
    driver.find_element_by_link_text('搜索设置').click()
    

    3、鼠标右键操作

       context_click 是触发鼠标右键操作的方法。

    #对 AC 类进行实例化
    actionChains = AC(driver)
    kw = driver.find_element_by_id('kw')
    #鼠标在百度输入框右键操作
    actionChains.context_click(kw)
    

    4、鼠标双击操作

      double_click 是触发鼠标双击的操作方法,一般使用在有数据交互的地方。比如,有这样一个业务,点击按钮会向数据库插入一条数据,而且只能插入一条数据,如果前端没有对双击进行处理的话,双击按钮后就会向数据库插入两条数据。

    su = driver.find_element_by_id('su')
    #对“百度一下”按钮双击操作
    actionChains.double_click(su)

    七、键盘事件实践

      Selenium 中提供了keys 模块中的 Keys 类来处理键盘事件的操作,如下:

    from selenium import webdriver
    import time as t
    from selenium.webdriver.common.keys import Keys
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('http://www.baidu.com')
    so = driver.find_element_by_id('kw')
    so.send_keys('python')
    t.sleep(3)
    '''
    使用键盘事件,把复制的关键字粘贴到bing搜索输入框中
    '''
    #选中输入框的搜索关键字
    so.send_keys(Keys.CONTROL,'a')
    #复制搜索的关键字
    so.send_keys(Keys.CONTROL,'c')
    t.sleep(3)
    #按下Backspace删除输入的关键字
    so.send_keys(Keys.BACKSPACE)
    t.sleep(3)
    
    driver.get('http://www.bing.com')
    bingso = driver.find_element_by_id('sb_form_q')
    #复制搜索关键字到bing搜索输入框中
    bingso.send_keys(Keys.CONTROL,'v')
    t.sleep(3)
    
    driver.quit()

    八、获取截图

      在自动化测试中,在测试执行期间有时需要获取截图信息,一方面可以定位错误的脚本,方便调试脚本,另一方面也可以以此为据,便于开发人员有效的交流。

    1、获取当前截图

      方法:save_screenshot

    driver.save_screenshot('tupian.png') # 在当前目录下生成 tupian.png 的图片

    2、保存当前屏幕快照

      方法:get_screenshot_as_file,可以填写完整的文件路径。

    driver.get_screenshot_as_file('D:/tupian.png')
    

    3、获取图片二进制数据

      方法:get_screenshot_as_png,该方法测试场景中使用较少。

    print(driver.get_screenshot_as_png())

     九、JavaScript 的处理

      在浏览器的滑动到底部或者顶部,对时间控件以及富文本等处理中,需要 JavaScript 的脚本配合,在 Selenium 中对 JavaScript 脚本调用的方法是 execute_script。

    1、浏览器的滑动操作

      如在百度搜索中,实现滑动到浏览器的底部或者顶部:

    from selenium import webdriver
    import time as t
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('http://www.baidu.com')
    driver.implicitly_wait(30)
    driver.find_element_by_id('kw').send_keys('selenium')
    driver.find_element_by_id('su').click()
    #浏览器活动到底部 js 代码
    down = "var q=document.documentElement.scrollTop=10000"
    t.sleep(3)
    #操作 js 实现鼠标滑动到浏览器底部
    driver.execute_script(down)
    t.sleep(3)
    #点击下一页
    driver.find_element_by_link_text('下一页>').click()
    t.sleep(3)
    #浏览器活动到顶部 js 代码
    up = "var q=document.documentElement.scrollTop=0"
    #先滑到底部
    driver.execute_script(down)
    t.sleep(3)
    #操作 js 实现鼠标滑动到浏览器顶部
    driver.execute_script(up)
    t.sleep(3)
    driver.quit()
    

    2、富文本的处理

      在 Web 产品中,有时需要对富文本中写入内容。富文本一般都在 iframe 框架中,可以通过 iframe 的 ID 或者索引的方式进入 iframe 中,再通过 JavaScript 的方式在富文本中输入需要的内容。如 iframe 的 ID 为 ueditor_0,在富文本中写入内容,可以单独写个可调用函数,并进入相应的位置后调用:

    from selenium import webdriver
    import time as t
    
    def richText(txt):
        '''往富文本中写入内容'''
        js = "document.getElementById('ueditor_0').contentwindow."
            "document.body.innerHTML='{0}'".format(txt)
        driver.execute_script(js)
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('富文本 URL 地址')
    richText('一起来学 Python 吧!')
    t.sleep(3)
    driver.quit()
    

    3、时间控件的处理

      时间控件经常出现在查询中,需要按某一时间段查询出数据并且来验证查询功能是否正确。大多数时间控件是只读属性的,在自动化测试中,处理只读属性的时间控件中输入时间。用 js 把禁止输入的 readonly 属性去掉,把它当成一个普通的 input 框处理。

      取消时间控件的只读属性,有四种方法:参考方法

    # 1.原生js,移除属性
    # js = "document.getElementById('txtBeginDate').removeAttribute('readonly')" 
    # 2.jQuery,移除属性
    # js = "$('input[id=txtBeginDate]').removeAttr('readonly')"
    # 3.jQuery,设置为false
    # js = "$('input[id=txtBeginDate]').attr('readonly',false)"
    # 4.jQuery,设置为空(同3)
    js = "$('input[id=txtBeginDate]').attr('readonly','')"
    
    driver.execute_script(js)
    

      步骤:首先取消时间控件的只读属性;然后在 input 输入框中给 value 赋值,填写需要输入的时间。

      如在 input 中 value placeholder=“开始时间≥当前时间”,编写开始和结束时间的可调用函数:

    def startJs(startTime):
        '''开始时间中输入自定义的时间,前一段是取消只读属性,后一段是输入开始时间'''
        js = "$("input[placeholder='开始时间≥当前时间']").removeAttr('readonly');$("input[placeholder='开始时间≥当前时间']").attr('value','{0}')".format(startTime)
        driver.execute_script(js)
    
    def endJs(endTime):
        '''结束时间中输入自定义的时间,前一段是取消只读属性,后一段是输入结束时间'''
        js = "$("input[placeholder='结束时间>开始时间']").removeAttr('readonly');$("input[placeholder='结束时间>开始时间']").attr('value','{0}')".format(endTime)
        driver.execute_script(js)
    

      时间控件中实现自定义输入代码:

    from selenium import webdriver
    import time as t
    
    def startJs(startTime):
        '''开始时间中输入自定义的时间,
        前一段是取消只读属性,后一段是输入开始时间'''
        js = "$("input[placeholder='开始时间≥当前时间']")." 
             "removeAttr('readonly');" 
             "$("input[placeholder='开始时间≥当前时间']")." 
             "attr('value','{0}')".format(startTime)
        driver.execute_script(js)
    
    def endJs(endTime):
        '''结束时间中输入自定义的时间,
        前一段是取消只读属性,后一段是输入结束时间'''
        js = "$("input[placeholder='结束时间>开始时间']")." 
             "removeAttr('readonly');" 
             "$("input[placeholder='结束时间>开始时间']")." 
             "attr('value','{0}')".format(endTime)
        driver.execute_script(js)
    
    driver = webdriver.Chrome()
    driver.maximize_window()
    driver.implicitly_wait(30)
    driver.get('时间控件的 URL 地址')
    
    startJs('2019-01-01 09:00:00')
    t.sleep(3)
    endJs('2019-12-12 23:59:59')
    t.sleep(3)
    driver.quit()
    

      

    这些方法还要在具体的 Python UI 自动化测试 项目中实践,灵活运用,才能真正的掌握!

    谢谢查看,笔记持续修改完善!

    2019-10-13

  • 相关阅读:
    Security and Cryptography in Python
    Security and Cryptography in Python
    Security and Cryptography in Python
    Security and Cryptography in Python
    Security and Cryptography in Python
    Security and Cryptography in Python
    Security and Cryptography in Python
    微信小程序TodoList
    C语言88案例-找出数列中的最大值和最小值
    C语言88案例-使用指针的指针输出字符串
  • 原文地址:https://www.cnblogs.com/yuntimer/p/11665833.html
Copyright © 2011-2022 走看看