Selenium基础

Selenium(1)环境搭建

1、selenium介绍css

selenium主要用于web应用程序的自动化测试,还支持全部基于web的管理任务自动化。html

selenium经历了2个版本,selenium1.0和selenium2.0;selenium不是一个单独的工具,而是由一些插件、类库构成,每一个组成部分都有其特色和应用场景。前端

selenium2.0由如下组件构成:python

selenium2.0 = selenium1.0 + Webdriverweb

Webdirver:经过原生浏览器支持或扩展来直接控制浏览器,针对各个浏览器开发,与浏览器紧密集成,支持建立更高级的测试,其还能够利用操做系统级的调用,模拟用户输入;chrome

selenium IDE:嵌入到Firefox浏览器中的一个插件,实现简单的浏览器操做录制与回放功能,主要用于快速建立BUG及重现脚本,可转化为多种语言;编程

selenium Gird:测试辅助工具,利用现有的计算机基础设施,实现多台计算上和异构环境中运行测试用例;设计模式

selenium RC:selenium的核心组件,支持多种不一样语言编写自动化测试脚本,经过其服务器做为代理服务器去访问应用,达到测试的目的;浏览器

             Client Libraries:Client Libraries库主要用于编写测试脚本,用来控制Selenium Server的库;安全

             Selenium Server:负责控制浏览器行为;

                              Selenium Core(一个JavaScript函数集合):被嵌入到浏览器中,经过它实现用程序对浏览器进行操做;

                              Launcher:用于启动浏览器,把Core加载到浏览器页面当中,并把浏览器代理设置为Selenium Server的HTTP Proxy

 

2、环境搭建

一、安装python

登陆Python官网,找到download,选择与自身平台(Windows/Linux)相符的版本下载(建议3.5+),而后安装便可;

注意:安装时选择安装界面的“Add Python 3.x to PATH”进行勾选,避免再次配置环境变量;

安装完成后经过Windows命令提示符CMD输入“python”,查看是否安装成功,以下图所示:

如上图所示,则证实安装成功;

 

二、安装setuptools与pip

setuptools是PEAK(Python enterprise Application Kit)的一个副项目,是python的distutilsde的加强工具,能够更方便建立和发布python包,特别是对其余包有依赖的状况;

pip是一个安装和管理python包的工具,经过pip来安装python包将变得很简单,省去了繁琐的过程,pip的安装依赖于setuptools,安装pip以前须要先安装setuptools;

注意:python目前不支持setuptools,所以须要使用distribute;

setuptools与pip的下载地址以下:

setuptools:https://pypi.python.org/pypi/setuptools

pip:https://pypi.org/project/pip/

注意: 最新版的python安装包中已经集成了pip,能够在安装目录下的script路径下查看是否有pip.exe或pip3.exe文件,若是有,则cmd命令行中输入pip进行验证;

如上图所示,则证实已经安装pip;

 

三、安装selenium

完成上面2个步骤以后,能够经过cmd命令直接安装selenium包,以下图所示:

注意:安装时若是只输入包名,则默认安装当前库中的最新版本,若是想安装本身须要的版本,则须要在包名后面加上版本号,好比:

pip install selenium==2.48.0

 

四、下载浏览器驱动

前面说过,selenium支持多种浏览器,因此只须要下载对应的浏览器驱动,将解压获得的exe文件放到python的安装目录下便可;

各个浏览器驱动下载地址:https://www.seleniumhq.org/download/

 

五、调试

打开一款python编译器,输入下面的代码,运行,查看是否成功调用浏览器运行,若是运行成功,则说明已成功搭建好自动化开发环境;

 

Selenium(2)WebDriver简介及元素定位

1、WebDriver原理

一、关于WebDriver

设计模式:按照Server-Client的经典设计模式设计;

Server端:即Remote Server(远程服务器),能够是任意的浏览器,当脚本启动浏览器时,该浏览器就是Remote Server,它的职责是等待Client发送请求并作出响应;

Client端:简单来讲就是咱们的测试代码,测试代码中的一些行为是以HTTP请求的方式发送给被测试浏览器——Remote Server,Remote Server接受请求,执行相应操做,

         并在Response中返回执行状态、返回值等信息;

 

二、WebDriver工做流程

①WebDriver启动目标浏览器,并绑定至指定端口,启动的浏览器实例将做为WebDriver的Remote Server;

②Client端经过CommandExcuter发送HTTPRequest给Remote Server的侦听端口(通讯协议:the webdriver wire protocol);

③Remote Server须要依赖原生的浏览器组件(好比:chromedriver.exe)来转化浏览器的native调用;

 

三、WebDriver.log

python提供了logging模块给运行中的应用,提供了一个标准的信息输出接口。它提供了basicConfig方法用于基本信息的定义,开启debug模块,

就能够捕捉到Client端向Server端发送的请求,例子以下:

1 # coding=utf-8
 2 # 导入logging模块,捕捉Client发送的请求
 3 from selenium import webdriver
 4 import logging
 5 from selenium import webdriver
 6 from selenium.webdriver.support.select import Select # select类
 7 from selenium.webdriver.common.by import By #By类:定位元素
 8 
 9 logging.basicConfig(level=logging.DEBUG)
10 driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
11 driver.get("www.baidu.com")
12 
13 driver.find_element_by_id("kw").send_keys("selenium")
14 driver.find_element_by_id("su").click()
15 driver.quit() 

2、WebDriver定位方法

WebDriver是基于selenium设计的操做浏览器的一套API,针对多种编程语言都实现了这套API,站在python角度来讲,WebDriver是python的一个用于实现Web自动化的第三方库。

一、WebDriver定位方法

WebDriver定位方法提供了八种元素定位方法,所对应的方法、特性分别是:

 

二、XPath和CSS的相似功能对比

 

三、用By定位元素

针对前面介绍的8种定位方法,WebDriver还提供另外一种方法,即:统一调用find_element()方法,经过By来声明定位方法,而且传入对应定位方法的定位参数,例子以下:

find.element()方法只用于定位元素,它须要两个参数,第一个参数是定位的类型,由By提供,第二个参数是定位的具体方式,在使用By以前须要将By类导入;

# 导入By类的包
from selenium.webdriver.common.by import By
find.element(by.id,"kw")
find.element(by.name,"wd")
find.element(by.class_name,"s_ipt")
find.element(by.tag_name,"input")
find.element(by.link_text,"新闻")
find.element(by.partial_link_text,"")
find.element(by.xpath,"//*[@class='bg s_btn'")
find.element(by.css_selector,"span.bg s_btn_wr>input#su")

四、定位一组元素

上面提到的8种定位方法,都是针对单个元素定位的,webdriver还提供了与之对应的8种用于定位一组元素的方法。其通常应用于如下场景:

①批量操做元素,例如勾选页面上全部的复选框;

②先获取一组元素,再从这组元素中过滤出须要操做的元素;

定位一组元素的方法与定位单个元素的用法类似,惟一的区别是在element后面多一个s表示复数,具体以下:

# webdriver提供的定位一组元素方法
id                    find_elements_by_id()
Name                  find_elements_by_name()
class_name            find_elements_by_class_name()
tag Name              find_elements_by_tag_name()          
link text             find_elements_by_link_text()
partial link text     find_elements_by_partial_link_text()
xpath                 find_elements_by_xpath()
css selector          find_elements_by_css_selector()

获取一组元素中某个元素的几个方法:

len():用来计算元素的个数,经过print()打印出计算的结果;

pos()或pop(-1):默认获取一组元素的最后一个元素,并返回该元素的值;

pop(0):默认获取一组元素的第一个元素,并返回该元素的值;

pop(1):默认获取一组元素的第二个元素,并返回该元素的值;

......

 

3、WebElement接口经常使用方法

一般须要与页面交互的方法都由WebElement接口提供,包括上面提到的8种定位方法,下面介绍经常使用的几种方法:

submit():用于提交表单,例如搜索框输入关键字以后的“回车”操做,例如:

# 提交表单
from select import webdriver
driver = webdriver.Chrome("安装工具\python\chromedriver.exe")
driver.get("http://www.baidu.com")
driver.find_element_by_id("kw").send_keys("imyalost")
# 提交输入框中的内容
driver.find_element_by_id("imyalost").submit()
driver.quit()

注意:有时候submit()方法和click()方法能够互用,但submit()的应用范围不及click()普遍;

clear():清除文本;

send_keys(*value):模拟按键输入;

click():单击元素;

size:返回元素的尺寸;

text:获取元素的文本;

get.attribute(name):得到属性值;

is_displayed():设置该元素是否用户可见;

# webelement接口经常使用方法
from selenium import webdriver
driver = webdriver.Chrome("安装工具\python\chromedriver.exe")
driver.get("http://www.baidu.com")
# 得到输入尺寸
size = driver.find_element_by_id("kw").size
print("size")
# 返回百度页面底部备案信息
text = driver.find_element_by_id("cp").text
print("text")
# 返回元素的属性值,能够是id、name、type或其余属性
attribute = driver.find_element_by_id("kw").get_attribute("type")
print("attribute")
# 返回元素结果是否可见,返回结果为True或Flase
result = driver.find_element_by_id("kw").is_displayed()
print("result")

 

Selenium(3)浏览器及鼠标,键盘事件

1、控制浏览器

webdriver主要提供操做页面上各类元素的方法,但它也提供操做浏览器的一些方法,例如控制浏览器大小、前进和后退等。

一、控制浏览器窗口大小

# 控制浏览器大小
from selenium import webdriver
driver = webdriver.Chrome("安装工具\python\chromedriver.exe")
driver.get("http://www.baidu.com")
# 参数数字为像素点
print("设置浏览器宽480、高800显示")
driver.set_window_size(480,800)

二、全屏显示

webdriver提供了maximize_window()方法使打开的浏览器全屏显示,其用法与set_window_size()相同。

三、控制浏览器前进、后退

如今的浏览器在浏览网页时都提供了前进和后退功能,webdriver也提供了对应的forward()和back()方法,来模拟前进和后退按钮:

# 控制浏览器前进、后退
from selenium import webdriver
driver = webdriver.Chrome("安装工具\python\chromedriver.exe")
# 访问百度首页
first_url='http://www.baidu.com''
print("now access %s "%(first_url))
driver.get(first_url)
# 访问新闻页面
second_url='http://www.news.baidu.com'
print("now access % s "%(second_url)")
driver.get("second_url")
# 后退到百度首页
print("back to %s "%(first_url)")
driver.back()
# 前进到新闻页
print("forward to %s "%(second_url)")
driver.forward()

为了看清脚本执行过程,每一步的操做都经过print()打印当前的URL地址,执行结果以下:

now access http://www.baidu.com

now access http://news.baidu.com

back to http://www.baidu.com

froward to http://news.baidu.com

四、模拟浏览器前刷新

通常咱们刷新页面都是经过F5或者页面上的刷新按钮,webdriver也提供了刷新方法refresh(),用来模拟页面刷新:

......

# 刷新当前页面

driver.refresh()

......

 

2、鼠标事件

在webelement接口提供的方法中,能够经过click()来模拟鼠标单击操做,但实际上鼠标交互方式不少,例如:右击、悬停、鼠标拖动等功能;

webdriver提供了ActionChains类,封装了鼠标操做的经常使用方法:

perform():执行全部的ActionChains中存储的行为

context_click():鼠标右击

double_click():鼠标双击

drag_and_drop():鼠标拖动

move_to_element():鼠标悬停

一、鼠标右击操做

# 鼠标右击操做
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
driver = webdriver.Chrome("安装工具\python\chromedriver.exe")
driver.get("http://www.baidu.com")
# 定位到要右击的元素
right_click = driver.find_element_by_id("KW")
# 对定位到的元素执行鼠标右击操做
ActionChains(driver).context_click(right_click).perform()
...

二、鼠标悬停

鼠标悬停弹出下拉菜单也是一个十分常见的功能设计,move_to_element()方法能够模拟鼠标悬停动做,其用法与context_click()相同;

1 # 鼠标悬停
2 ...
3 above = driver.find_element_by_id("id")
4 ActionChains(driver).move_to_element(above).perform()
5 ... 

三、鼠标双击操做

double_click()方法用于模拟鼠标双击操做;

1 # 鼠标双击操做
2 ...
3 double_click = driver.find_element_by_id("id")
4 ActionChains(driver).double_click(double_click).perform()
5 ...

四、鼠标拖放操做

drag_and_drop(source,target)在源元素上按住鼠标左键,而后移动到目标元素上释放;

source:鼠标拖动的源元素

target:鼠标释放的目标元素

# 定位元素的位置
...
element = driver.find_element_by_id("id")
# 定位元素要移动到的目标位置
target = driver.find_element_by_id("xx")
# 执行元素的拖放操做
ActionChains(driver).drag_and_drop(element,target).perform()
...

3、键盘事件

Keys()类提供了键盘上几乎全部的按键方法,send_keys()不见能够模拟键盘输入,还能够用来输入键盘上的按键,甚至是组合键,例子以下:

# 模拟键盘事件
from selenium import webdriver
# 引入keys模块
from selenium.webdriver.common.keys import Keys
driver = webdriver.Chrome("安装工具\python\chromedriver.exe")
driver.get("http://www.baidu.com")
# 输入框输入内容
driver.find_element_by_id("kw").send_keys("selenium")
# 输入“教程”
driver.find_element_by_id("kw").send_keys("教程")
# 删除“教程”
driver.find_element_by_id("kw").send_keys(Keys.BACK_SPACE)
...

如下为经常使用的键盘操做:

# 经常使用的键盘操做
send_keys(Keys.BACK_SPACE)
send_keys(Keys.SPACE)
send_keys(Keys.TAB)
send_keys(Keys.ESCAPE)
send_keys(Keys.ENTER)
send_keys(Keys.CONTROL,'a')
send_keys(Keys.CONTROL,'c')
send_keys(Keys.CONTROL,'v')
send_keys(Keys.CONTROL,'x')
send_keys(Keys.F1)
...
send_keys(Keys.F12)

以上为webdriver的控制浏览器操做以及模拟键盘、鼠标操做的经常使用方法,固然具体在实际使用过程当中,还须要结合实际的业务场景,灵活运用

 

Selenium(4)断言

在编写自动化测试脚本时,为了使“机器”去自动辨识test case的执行结果是True仍是False,通常都须要在用例执行过程当中获取一些信息,来判断用例的执行时成功仍是失败。

判断成功失败与否,就涉及到断言。webdriver的断言使用有三种模式:操做(action)、辅助(accessors)、断言(assertion)。

 

一、操做(action)

模拟用户与Web应用程序的交互,通常用于操做应用程序的状态;

如点击连接,选择选项的方式进行工做;若是一个动做执行失败,或是有错误,当前的测试将会中止执行。

常见命令以下:

open(打开页面)

click(点击)

clickAndWait(点击并等待)

type(文本类型)

select(选择下拉菜单)

selectWindow(选择弹出窗口)

pause(等待指定时间,以毫秒为单位,即要睡眠的时间)

setSpeed(设定执行速度。以毫秒延迟间隔长度。默认没有延迟,即为0)

setTimeout(指定等待动做完成的等待时间。默认为30秒,须要等待的动做包括了OPEN 和WAITFOR)

goBack(模拟用户点击其浏览器上的“back”按钮)

close(模拟用户点击弹出窗体或表单标题栏上的”关闭”按钮)

 

二、辅助(accessors)

辅助工具,用于检查应用程序的状态并将结果存储到变量中;

如:storeElementPresent(locator,variableName)

其中参数locator表示元素定位器,variableName用于存储结果的变量名;

即将locator定位到的状态存储到variableName变量中,若是该元素出现返回true,不然返回false,可同断言一同使用。

 

三、断言(assertion)

验证应用程序的状态是否同所指望的一致。

常见的断言包括:验证页面内容,如标题是否为X或当前位置是否正确,或是验证该复选框是否被勾选。

经常使用断言以下:

assertLocation(判断当前是在正确的页面)

assertTitle(检查当前页面的title是否正确)

assertValue(检查input的值, checkbox或radio,有值为”on”无为”off”)

assertSelected(检查select的下拉菜单中选中是否正确)

assertSelectedOptions(检查下拉菜单中的选项的是否正确)

assertText(检查指定元素的文本)

assertTextPresent(检查在当前给用户显示的页面上是否有出现指定的文本)

assertTextNotPresent(检查在当前给用户显示的页面上是否没有出现指定的文本)

assertAttribute(检查当前指定元素的属性的值)

assertTable(检查table里的某个cell中的值)

assertEditable(检查指定的input是否能够编辑)

assertNotEditable(检查指定的input是否不能够编辑)

assertAlert(检查是否有产生带指定message的alert对话框)

waitForElementPresent (等待检验某元素的存在,为真时,则执行)

使用断言的注意点:

①不要使用断言做为公共方法的参数检查,公共方法的参数永远都要执行;

②断言语句不能够有任何边界效应,不要使用断言语句去修改变量和改变方法的返回值;

 

Selenium(5)解决页面元素display:none的方法

在UI自动化测试中,有时候会遇到页面元素没法定位的问题,包括xpath等方法都没法定位,是由于前端元素被设置为不可见致使。

 

一、具体问题

常见的页面元素不可见致使的不可定位,都是因为下面的问题:

经过查看相关文档,能够看出display:none方法是设置元素不可见,这就是致使为何经过定位页面元素没法定位的缘由。

 

二、解决方案

对于这种问题,能够经过JavaScript修改页面元素属性来将元素置位可见,而后经过id、classname等方法去定位,示例代码以下(针对上图所示):

js = "document.getElementById(\"txtPassword\").style.display='block';"
# 调用js脚本
driver.execute_script(js)
sleep(3)
driver.find_element_by_id("txtPassword").send_keys("123456")

代码解析:

首先经过selenium封装好的方法document去找到display元素,document提供如下方法来定位display元素:

getElementById():返回对指定ID第一个对象的引用

getElementsByName() :返回带有指定名称的对象集合

getElementsByTagName():返回带有指定标签名的对象集合

上面我定义了一个js变量,而后经过getElementById()方法去引用display元素,修改none属性为block属性(做为块级元素显示),而后经过selenium自带的execute_script方法执行脚本。

最后,当元素属性置为可见时,能够经过ID去定位元素。

 

其实还有一个解决方案:让前端修改display:none为block就行了,但这样的话,带来的变化和安全风险又是须要考虑的问题。一个问题的解决老是伴随着新的问题,核裂变了解一下?

想起今天和同行聊天时提及的分裂BUG的话题,对话以下:

大佬N:核裂变的原理是经过中子撞击原子核产生多个新的原子核,原子核是已有的BUG,中子是修改BUG加上的代码,分裂以后这个bug消失了,取而代之的是更多的原子核(BUG)。。。

我:引发一个BUG的缘由多是多个,修改一段代码可能形成多个BUG,就像用新技术解决旧问题而带来的新问题一个意思。。。

 

自动化自己最大的挑战仍是变化,所以从分层测试角度结合公司项目具体状况,考虑解决问题的方法,才是最好的选择。

 

Selenium(6)利用Select模块处理下拉框

在利用selenium进行UI自动化测试过程当中,常常会遇到下拉框选项,这篇博客,就介绍下如何利用selenium的Select模块来对标准select下拉框进行操做。。。

 

首先导入Select模块:

1 # coding=utf-8
2 from selenium import webdriver
3 from selenium.webdriver.support.select import Select

感兴趣的能够将鼠标指向Select,而后按住Ctrl鼠标单击,查看Select模块的源码,是如何定义封装Select的各个方法的。

一、Select提供了三种选择某一项的方法

1 select_by_index          # 经过索引定位
2 select_by_value          # 经过value值定位
3 select_by_visible_text   # 经过文本值定位

注意事项:

index索引是从“0”开始;

value是option标签的一个属性值,并非显示在下拉框中的值;

visible_text是在option标签中间的值,是显示在下拉框的值;

 

二、Select提供了三种返回options信息的方法

1 options                  # 返回select元素全部的options
2 all_selected_options     # 返回select元素中全部已选中的选项
3 first_selected_options   # 返回select元素中选中的第一个选项

注意事项:

这三种方法的做用是查看已选中的元素是不是本身但愿选择的:

options:提供全部选项的元素列表;

all_selected_options:提供全部被选中选项的元素列表;

first_selected_option:提供第一个被选中的选项元素;

 

三、Select提供了四种取消选中项的方法

1 deselect_all             # 取消所有的已选择项
2 deselect_by_index        # 取消已选中的索引项
3 deselect_by_value        # 取消已选中的value值
4 deselect_by_visible_text # 取消已选中的文本值

注意事项:

在平常的web测试中,会常常遇到某些下拉框选项已经被默认选中,这种时候就须要用到这里所说的四种方法;

 

下面以实际的代码来作个示例,被测试网页与源码截图以下:

好比要选择3线,那么三种选择方法示例代码以下:

# coding=utf-8
from selenium import webdriver
from selenium.webdriver.support.select import Select
from time import sleep

# 登陆
driver = webdriver.Chrome()
......

# 根据索引选择
Select(driver.find_element_by_name("storeDeclare.cityLine")).select_by_index("3")
# 根据value值选择
Select(driver.find_element_by_name("storeDeclare.cityLine")).select_by_value("3线")
# 根据文本值选择
Select(driver.find_element_by_name("storeDeclare.cityLine")).select_by_visible_text("3线")
sleep(5)
driver.quit()

以上就是关于selenium的Select模块提供的几种方法的用法,示例代码只是示例,具体实践还须要结合实际的工做须要来进行

 

Selenium(7)三种等待方式

UI自动化测试,大多都是经过定位页面元素来模拟实际的生产场景操做。但在编写自动化测试脚本中,常常出现元素定位不到的状况,究其缘由,无非两种状况:一、有frame;二、没有设置等待。

由于代码运行速度和浏览器加载渲染速度,不是一个量级,因此致使了这种状况发生。webdriver提供了3种类型的等待:显式等待、隐式等待、强制等待。

 

一、显示等待

定义:等待某个条件成立时继续执行,不然在达到最大时长时抛出异常(TimeoutException);

WebDriverWait类是由webdriver提供的等待方法,配合该类提供的until()和until_not()方法一块儿使用,就能够根据判断条件而灵活进行等待,格式以下:
WebDriverWait(driver,timeout,poll_frequency=0.5,ignored_exceptions=None)
driver:浏览器驱动
timeout:最长超时时间
poll_frequency:检测间隔时间,默认0.5s
ignored_exceptions:超时后的异常信息,默认状况抛出NoSuchElementException异常
WebDriverWait()通常由until()或until_not方法配合使用,下面是这两种方法的说明:
until(method,message=''):调用该方法提供的驱动程序做为一个参数,直到返回值为True;
until_not(method,message=''):调用该方法提供的驱动程序做为一个参数,直到返回值为Flase;

示例代码以下:

# coding = utf-8
from selenium import webdriver
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
 
driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
driver.implicitly_wait(10)
driver.get('http://www.cnblogs.com/imyalost/')
locator = (By.LINK_TEXT, '老_张')
 
try:
    WebDriverWait(driver, 20, 0.5).until(EC.presence_of_element_located(locator))
    print(driver.find_element_by_link_text('老_张').get_attribute('href'))
finally:
    driver.close()

代码解析:

本例中,经过as关键字将expected_conditions重命名为EC,并调用presence_of_element_located()方法判断元素是否存在;

上面的例子中,同时使用了隐性等待和显性等待,可是须要注意的是:等待的最长时间取二者之中的最大值;

expected_conditions类提供的预期条件判断方法以下:
title_is: 判断当前页面的title是否彻底等于(==)预期字符串,返回布尔值
title_contains : 判断当前页面的title是否包含预期字符串,返回布尔值
presence_of_element_located : 判断某个元素是否被加到了dom树里,并不表明该元素必定可见
visibility_of_element_located : 判断某个元素是否可见. 可见表明元素非隐藏,而且元素的宽和高都不等于0
visibility_of : 跟上面的方法作同样的事情,只是上面的方法要传入locator,这个方法直接传定位到的element就行了
presence_of_all_elements_located : 判断是否至少有1个元素存在于dom树中。举个例子,若是页面上有n个元素的class都是‘column-md-3‘,那么只要有1个元素存在,这个方法就返回True
text_to_be_present_in_element : 判断某个元素中的text是否 包含 了预期的字符串
text_to_be_present_in_element_value : 判断某个元素中的value属性是否 包含 了预期的字符串
frame_to_be_available_and_switch_to_it : 判断该frame是否能够switch进去,若是能够的话,返回True而且switch进去,不然返回False
invisibility_of_element_located : 判断某个元素中是否不存在于dom树或不可见
element_to_be_clickable : 判断某个元素中是否可见而且是enable的,这样的话才叫clickable
staleness_of : 等某个元素从dom树中移除,注意,这个方法也是返回True或False
element_to_be_selected : 判断某个元素是否被选中了,通常用在下拉列表
element_selection_state_to_be : 判断某个元素的选中状态是否符合预期
element_located_selection_state_to_be : 跟上面的方法做用同样,只是上面的方法传入定位到的element,而这个方法传入locator
alert_is_present : 判断页面上是否存在alert

二、隐式等待

定义:经过设定的时长等待页面元素加载完成,再执行下面的代码,若是超过设定时间还未加载完成,则继续执行下面的代码(注意:在设定时间内加载完成则当即执行下面的代码);

隐式等待的方法为:implicitly_wait,示例代码以下:

# coding = utf-8
from selenium import webdriver
 
driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
driver.implicitly_wait(10) # 隐性等待,最长等10秒
driver.get('http://www.cnblogs.com/imyalost/')
 
print(driver.current_url)
driver.quit()

代码解析:

本例中,设置的等待时长为10秒,但这10秒并不是一个固定时间,并不影响脚本执行速度;其次,隐式等待对整个driver的周期都起做用,所以只须要设置一次便可。

 

三、强制等待

即sleep()方法,由python中的time模块提供,强制让代码等待xxx时间,不管前面的代码是否执行完成或者还未完成,都必须等待设定的时间。

示例代码以下:

# coding = utf-8
from selenium import webdriver
from time import sleep
 
driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
driver.get('http://www.cnblogs.com/imyalost/')

sleep(5)
 
print(driver.current_url)
driver.quit()

代码解析:

本例中,设置强制等待时间为5秒,5秒以后,打印获取到的当前页面的url,而后关闭窗口。

这种强制等待的方法,在debug时候颇有用,不过建议慎用这种方法,由于太死板,严重影响程序执行速度!

 

以上三种等待方法,在具体的场景中须要根据状况选择合适的方法,灵活运用。。。

 

Selenium(8)Html测试报告

自动化测试过程当中,得到用例的执行结果后,须要有具象化、简洁明了的测试结果,好比:用例执行时间、失败用例数、失败的缘由等,这时候,就须要用到测试报告。

HTML测试报告是python语言自带的单元测试框架,其扩展的HTMLTestRunner模块可用于生成易于使用的HTML测试报告。

 

一、HTMLTestRunner下载

下载地址:http://tungwaiyip.info/software/HTMLTestRunner.html

下载完成后,将下载的文件保存到C盘的\Python35\Lib目录下(能够经过以下命令获取python安装目录):

①进入cmd命令行

②输入python

③输入import sys

④输入print(sys.path)

C:\Users\dell>python
Python 3.5.1 (v3.5.1:37a07cee5969, Dec  6 2015, 01:54:25) [MSC v.1900 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import sys
>>> print(sys.path)
['', 'C:\\Users\\dell\\AppData\\Local\\Programs\\Python\\Python35\\python35.zip', 'C:\\Users\\dell\\AppData\\Local\\Programs\\Python\\Python35\\DLLs',
  'C:\\Users\\dell\\AppData\\Local\\Programs\\Python\\Python35\\lib', 'C:\\Users\\dell\\AppData\\Local\\Programs\\Python\\Python35', 'C:\\Users\\dell\\
  AppData\\Local\\Programs\\Python\\Python35\\lib\\site-packages']

 

二、修改HTMLTestRunner文件

由于HTMLTestRunner是基于python2开发的,为了使其支持python3的环境,须要对其中的部份内容进行修改,修改后的内容以下:

# HTMLTestRunner修改内容
# 第94行
import io
# 第539行
self.outputBuffer = io.StringIO()
# 第631行
print(sys.stderr, '\nTime Elapsed: %s' % (self.stopTime-self.startTime))
# 第642行
if not cls in rmap:
# 第766行
uo = o
# 第772行
ue = e

三、python文件执行与调用

①python文件的后缀为.py

②py文件既能够用来执行,就像一小段程序,也能够用来做为模块被导入

③在python中导入模块通常用import

代码以下:

from selenium import webdriver
import unittest
import time

class MyTest(unittest.TestCase):
    def setUp(self):
        self.driver = webdriver,Chrome("F:\安装工具\python\chromedriver.exe")
        self.driver.maximize_window()
        self.driver.implicitly.wait(10)
        self.base_url = "http://www.baidu.com"

    def test_baidu(self):
        driver = self.driver
        driver.get(self.base_url + "/")
        driver.find_element_by_id("kw").clear()
        driver.find_element_by_id("kw").send_key("unittest")
        driver.find_element_by_id("su").click()
        time.sleep(2)
        title = assertEqual(title,"unittest_百度搜索")

    def tearDown(self):
        self.driver.quit()

if __name__ == "__main__":
    unittest.main()

 

四、HTMLTestRunner测试报告

以上面的test_baidu.py文件为例子,生成HTMLTestRunner测试报告,代码以下:

from selenium import webdriver
import unittest
from HTMLTestRunner import HTMLTestRunner

class Baidu(unittest.TestCase):
    def setUp(self):
        self.driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
        self.driver.implicitly_wait(10)
        self.base_url = "http://www.baidu.com/"

    def test_baidu_search(self):
        driver = self.driver
        driver.get(self.base_url)
        driver.find_element_by_id("kw").send_key("HTMLTestRunner")
        driver.find_element_by_id("su").click()

    def tearDown(self):
        self.driver.quit()


if __name__ == "__main__":
    baidu = Baidu("test_baidu_search")
    testunit = unittest.TestSuite()
    testunit.addTest(baidu)

    # 定义报告存放路径
    fp = open('./result.html', 'wb')
    # 定义测试报告
    runner = HTMLTestRunner(stream=fp,
                        title='百度搜索测试报告',
                        description= '用例执行状况:')
    runner.run(testunit) #运行测试用例
    fp.close() #关闭报告文件

代码简析:

①将HTMLTestRunner模块用import导入

②经过open()方法以二进制写模式打开当前目录下的result.html,若是没有则自动建立该文件

③调用HTMLTestRunner模块下的HTMLTestRunner类,stream指定测试报告文件,title用于定义测试报告的标题,description用于定义测试报告的副标题

④经过HTMLTestRunner的run方法运行测试套件中所组装的测试用例,最后经过close()关闭测试报告文件

 

Selenium(8)集成测试报告

随着软件不断迭代功能愈来愈多,对应的测试用例也会呈指数增加。一个实现几十个功能的项目,对应的用例可能有上百个甚至更多,若是所有集成在一个文件中,那么这个文件就很臃肿且维护麻烦。

一个很好的方法就是将这些用例按照功能类型进行拆分,分散到不一样测试文件中,即一个项目,对应多个分支。

 

1、分拆后的实现代码

一、testbaidu.py

from selenium import webdriver
import unittest
import time

class MyTest(unittest.TestCase):
    def setUp(self):
        self.driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
        self.driver.maximize_window()
        self.driver.implicitly.wait(10)
        self.base_url = "http://www.baidu.com"

    def test_baidu(self):
        driver = self.driver
        driver.get(self.base_url + "/")
        driver.find_element_by_id("kw").clear()
        driver.find_element_by_id("kw").send_key("unittest")
        driver.find_element_by_id("su").click()
        time.sleep(2)
        title = assertEqual(title,"unittest_百度搜索")

    def tearDown(self):
        self.driver.quit()

 

二、testyoudao.py

from selenium import webdriver
import unittest
import time

class Mytest(unittest.TestCase):

    def setUp(self):
        self.driver = webdriver.Chrome("F:\安装工具\python\chromedriver.exe")
        self.driver.maximize_window()
        self.driver.implicitly_wait(10)
        self.base_url = "http://www.youdao.com"
    
    def test_youdao(self):
        driver = self.driver
        driver.get(self.base_url + "/")
        driver.find_element_by_id("query").clear()
        driver.find_element_by_id("query").send.keys("webdriver")
        driver.find_element_by_id("qb").click()
        time.sleep(2)
        title = driver.title
        self.assertEqual(title, "webdriver - 有道搜索")

    def tearDown(self):
        self.driver.close()

 

2、建立用于执行全部用例的ALL_HTMLtest.py文件

一、ALL_HTMLtest.py

# coding=utf-8
import unittest
import time
from HTMLTestRunner import HTMLTestRunner

# 加载用例testbaidu,testyoudao
import testbaidu
import testyoudao

# 将测试用例添加到测试集中
suite = unittest.TestSuite()

suite.addTest(testbaidu.MyTest("test_baidu"))
suite.addTest(testyoudao.Mytest("test_youdao"))

if __name__ == '__main__':
    # 执行测试
    runner = unittest.TextTestRunner()
    runner.run(suite)

 

拆分带来的好处显而易见,能够根据不一样功能建立不一样的测试文件,甚至不一样的目录,还能够将不一样的小功能划分为不一样的测试类,在类下编写测试用例,总体结构更加清晰。

但依然存在缺陷(当用例达到成百上千条时,在ALL_HTMLtest.py中addTest()添加测试用例就变得很麻烦)。。。

 

二、TestLoader类

unittest单元测试框架提供了TestLoader类,该类负责根据各类标准加载测试用例,并将它们返回给测试套件。

unittest提供了能够共享的defaultTestLoader类,可使用其子类和方法建立实例,discover()方法就是其中之一。

discover(start_dir, pattern='test*.py', top_level_dir=None)

找到指定目录下的全部测试模块,并递归查找子目录下的测试模块,只有匹配到文件名才能被加载,若是启动的不是顶层目录,则顶层目录必须单独指定。

start_dir:要测试的模块名或测试用例目录;

pattern='test*.py':表示用例文件名的匹配原则,下面的例子中匹配文件名为以“test”开头的“.py”文件,星号“*”表示任意多个字符;

top_level_dir=None:测试模块的顶层目录,若是没有顶层目录,默认为None;

# coding=utf_8
import unittest
from unittest import defaultTestLoader
# 定义测试用例的目录为当前目录
test_dir = './'
discover = unittest.defaultTestLoader.discover(test_dir,pattern='test*.py') 

if __name__ == '__main__':
    runner = unittest.TextTestRunner()
    runner.run(discover)

 

3、集成测试报告

HTMLTestRunner目前只针对单个测试文件生成测试报告,所以须要对上面的代码进行修改,修改后内容以下:
# coding=utf_8
import unittest
import time
from unittest import defaultTestLoader
from HTMLTestRunner import HTMLTestRunner

# 定义测试用例的目录为当前目录
test_dir = './report'
discover = unittest.defaultTestLoader.discover(test_dir,pattern='test*.py') 

if __name__ == '__main__':
    now = time.strftime("%Y-%m-%d %H_%M_%S")
    filename = test_dir + '/' + now + 'result.html'
    fp = open(filename, 'wb')
    runner = HTMLTestRunner(stream=fp,title='集成测试报告demo',description= '用例执行状况:')
    runner.run(discover)
    fp.close()

 

执行后,结果以下:

 

 

转载: https://www.cnblogs.com/imyalost

相关文章
相关标签/搜索