自动化的执行步骤:
1)元素定位:定位到你想要操作的页面元素
2)操作该页面元素。例如:点击、输入、选择……
WebDriver API
Selenium提供的WebDriver API是一套用于定位操作浏览器页面元素的API(别人写好的方法、属性、类供开发人员调用)。
站在编程语言的角度(例如Python),WebDriver是Python用于实现Web UI自动化的一个第三方库。
站在WebDriver的角度,它针对多种编程语言实现了一遍这套API。
在WebDriver API里,有一个WebElement类,它里面定义了元素定位的方法。
Selenium WebDriver的特点如下:
- 简洁明快:WebDriver 易于上手,是一种简洁而紧密的编程接口,可以通过多种编程语言(例如Python、Java、C#、Ruby等)来调用WebDriver。
- 支持全部主流浏览器:例如Firefox、Safari、Edge、Chrome 及Internet Explorer等,在这些浏览器中的自动化操作等同于按真实用户的方式进行交互。
- WebDriver标准是W3C标准:主要的浏览器厂商(Mozilla、Google、Apple、Microsoft等)都支持WebDriver标准,将据此优化浏览器及开发控制代码(可将控制代码称为驱动程序,各个浏览器拥有自身的WebDriver驱动程序),提供更统一的原生操作支持,使自动化脚本更加稳定。
1、基本元素定位方法介绍
元素定位方法包含了2个系列:
- find_element系列:用于定位单个的页面元素
- find_elements系列:用于定位一组(多个)页面元素
每个系列提供了8种元素定位方法:
分组 | 解释说明 | ||||||||
id | 在页面元素有ID的情况下,优先考虑使用ID定位 但是ID属性可能不存在,也可能动态生成(也就是:页面刷新之后,元素ID可能会发生变化),因此还需要其他元素定位方法进行补充
可以在项目早期时就提出需求,对核心业务、核心流程中的页面元素进行元素ID设置,以便于后期测试 | ||||||||
name |
| ||||||||
link |
| ||||||||
其他比较灵活和复杂的定位方法 | xpath和cssd定位方法基本可以准确定位页面上的所有元素,但需要相应掌握对应的语法
|
以上8种元素定位方法(find_element_by_xxx)共同的特点如下:
1)如果页面上有匹配的元素,它会返回找到的页面元素,返回值的数据类型是WebElemen对象;
2)如果页面上没有匹配的元素,则该方法会报错,引发一个NoSuchElementExcept异常;
3)如果页面上有多个匹配的元素,通常情况下,只返回找到的第一个匹配的元素(注意:做元素定位的时候,尽量不要去使用有可能取多个但是定位第一个的情况,因为不同软件的实现可能不同,这个状态不确定,应该尽量写准确,能定位到某一个元素。)
find_elements_by_xxx系列也包含上述8种元素定位方法,只不过:
1)它返回的是一个包含WebElement对象的列表;
2)如果没有找到任何元素,不会报错,返回一个空的列表,长度为0
2、xpath表达式定位
Xpath是一种在XML文档中定位元素的语言。
html可以看做是xml的一种实现,两者都是由标签和文本组成,因此,selenium可以使用相应的语言来进行元素定位
Xpath定位方式 | 解释说明 |
(1)使用绝对路径的方式来定位 | 指的是从网页的HTML代码结构的最外层一层层的写到需要被定位的页面元素为止。 绝对路径起始于/,每一层都被/所割。 案例:/html/body/div[2]/form/input[3] 注解:
|
(2)使用相对路径的方式来定位 | 使用相对路径方式定位使用更多 不是从根目录写起,而是从网页文本的任意目录开始写。 相对路径起始于//,//所表示的含义是“任意目录下” 案例://input[@id=’kw’] 注解: 示例的含义:在当前页面查找任意目录下的input元素,且该元素的id属性取值为kw
|
3、css选择器定位
CSS选择器在CSS里用于选择页面上的特定元素来应用某种样式。
CSS选择器可用于定位页面元素。
常用的几种选择器:
选择器类型 | 解释说明 |
类选择器 | .xxx 选择class属性为xxx的元素 |
id选择器 | #xxx 选择id属性为xxx的元素 |
元素选择器 | xxx 选择标签名为xxx的元素 |
属性选择器 | [yyy=’bbb’]选择yyy属性取值为bbb的元素 此处:bbb外面的引号可以不写,如果加了引号,需要跟外层的引号进行区分 xpath的引号不能省略 |
在CSS里标识层级关系使用的是>(xpath里使用的是/)
案例:div#xx1>input.yy2 | 找的元素是:input标签 |
注意:对于CSS的属性值来说,可以加引号也可以不加,注意属性的引号和整个CSS表达式的引号要进行区分。对于xpath的属性值来讲,需要加上引号,否则报错。
CSS定位 | Xpath定位 |
find_element_by_css_selector(‘aa.xx’) find_element_by_css_selector(‘aa#xx’) find_element_by_css_selector(‘aa[yy=xx]’) find_element_by_css_selector(‘aa[yy=”xx”]’) find_element_by_css_selector(“aa[yy=’xx’]”) find_element_by_css_selector(“aa[yy=xx]”) | find_element_by_xpath(‘//aa[@class=”xx”]’) find_element_by_xpath(‘//aa[@id=”xx”]’) find_element_by_xpath(‘//aa[@yy=”xx”]’) find_element_by_xpath(“//aa[@yy=’xx’]”) |
也可以通过开发者工具来获取CSS选择器:
f12——》使用元素拾取器在你想要定位的元素上面点一下,代码区域就会高亮显示出该元素所对应的代码,再在该代码上右击,选择“复制”——》选择“CSS选择器”——》到需要使用CSS表达式的地方黏贴就能看到这个表达式:#kw
4、多浏览器测试
WebDriver API实例:浏览器百度搜索selenium后关闭:
|
前置条件:
- selenium支持的浏览器
- 本地安装了相应浏览器
- 配置了浏览器驱动
几个注意事项:
- 浏览器的首字母大写,比如br = webdriver.Firefox()
- 浏览器名称后面的括号不能遗漏,比如:br = webdriver.Chrome()
5、被测环境准备
安装论坛
注意:如果由于本地数据库或者PHP冲突,前期修改了端口号,登陆时需要在URL路径里声明端口号,比如:localhost:8080,数据库:localhost:3307
元素定位案例:论坛用户登录
步骤 | 解释说明 | ||||
1、启动浏览器 | # step1:启动浏览器 br = webdriver.Chrome() | ||||
2、打开网页(get网址) | # step2:打开网页 br.get("http://localhost:8080/upload/forum.php") | ||||
3、通过元素定位,定位到用户登陆框 | 具体操作:点击用户登陆框,按F12,启动开发者工具,按下元素定位,点击需要定位的元素 网页定位到对应元素,并可查看安元素相关信息 为了防止手工输入与源码不一致导致后续问题,通过鼠标点击对应元素选择相应的信息进行复制 一般来说,有元素ID的情况下选择ID定位, 这里复制的内容是:ID属性,即:ls_username
密码定位方法与上述类似 br.find_element_by_id("ls_username").send_keys("admin") br.find_element_by_id("ls_password").send_keys("123456") 点击登录按钮,可以通过再点击按钮上右击,选择检查,进行元素定位, 登录按钮没有对应的id,可以考虑通过复制其Xpath路径进行定位 路径://*[@id="lsform"]/div/div/table/tbody/tr[2]/td[3]/button 注意,如果Xpath路径本身包含了引号,元素定位中的引号需要和路径内的引号进行区分,比如:find_element_by_xpath('路径本身包含有""双引号') 一个案例: br.find_element_by_xpath('//*[@id="registerformsubmit"]/strong').click() #Xpath定位提交按钮 |
6、文本的清空(clear)和提交(submit)
主要的应用场景:
当页面上的某一个元素被反复利用时,比较好的办法是将页面元素保存为变量值,然后调用这个变量,从而简化测试代码的编写
案例:文本清空和提交的常规流程
from selenium import webdriver from time import sleep #启动浏览器 br=webdriver.Firefox() sleep(2) #打开论坛首页 br.get("http://localhost/upload/forum.php") sleep(2) #定位到搜贴的文本输入框,输入test br.find_element_by_id("scbar_txt").send_keys("test") sleep(2) #清空文本内容 br.find_element_by_id("scbar_txt").clear() sleep(2) #再次输入selenium br.find_element_by_id("scbar_txt").send_keys("selenium") sleep(2) #提交输入的内容 br.find_element_by_id("scbar_txt").submit() sleep(2) br.quit() |
优化点:上述四个步骤都是基于同一个页面元素进行操作的额,也就是id为scbar_txt的页面元素
e=br.find_element_by_id("scbar_txt")
优化后的代码:
from selenium import webdriver from time import sleep
#启动浏览器 br=webdriver.Firefox() sleep(2) #打开论坛首页 br.get("http://localhost/upload/forum.php") sleep(2) #定位到搜贴的文本输入框 e=br.find_element_by_id("scbar_txt") #输入test e.send_keys("test") sleep(2) #清空文本内容 e.clear() sleep(2) #再次输入selenium e.send_keys("selenium") sleep(2) #提交输入的内容 e.submit() sleep(2) br.quit() |
7、获取页面标题和源代码
注意:title和page_source是页面元素的一种属性(区分于方法,方法后面有()括号),属性后面不需要加括号
from selenium import webdriver from time import sleep
#启动浏览器 br=webdriver.Firefox() sleep(2) #打开论坛首页 br.get("http://localhost/upload/forum.php") sleep(2) #获取当前页面的标题 print(br.title) #获取当前页面的源代码 print(br.page_source) br.quit() |
8、浏览器的几个常用操作:最大化,刷新,往后退一页,往前进一页
from selenium import webdriver from time import sleep
#启动浏览器 br=webdriver.Firefox() #打开论坛首页 br.get("http://localhost/upload/forum.php") br.find_element_by_link_text("立即注册").click() #通过链接文本进行元素定位 br.maxmize_window() #窗口最大化 br.refresh() #刷新 br.back() #后退一页 br.forward() #前进一页 br.quit() |