python & selenium 自动化测试
python
+selenium
总整理
1 安装包和驱动
1.1 包
pip install selenium
1.2 驱动
1.3 查看浏览器版本
-
chrome://version/
-
注:使用该方式查看浏览器版本时,会自动更新最近版本浏览器。
2 调用浏览器
2.0 导入相关包
from selenium import webdriver
# Keys 用来模拟键盘按键,如`F1`
from selenium.webdriver.common.keys import Keys
2.1 主流浏览器
-
Google
webdriver.Chrome()
-
Firefox
webdriver.Firefox()
-
IE
webdriver.Ie()
-
Safari
webdriver.Safari()
-
Edge
webdriver.Edge()
2.2 优化用户体验
-
旧版浏览器
option = webdriver.ChromeOptions() option.add_experimental_option("useAutomationExtension", False) option.add_experimental_option('excludeSwitches', ["ignore-certificate-errors"]) driver = webdriver.Chrome(options=option)
-
最新版浏览器
option = webdriver.ChromeOptions() option.add_argument('disable-infobars') driver = webdriver.Chrome(options=option)
2.3 打开指定网页
url = 'http://www.baidu.com'
driver.get(url)
2.4 获取当前网址
url = driver.current_url # 用于跳转界面
3 查找元素
<html>
<head>
<title>index</title>
</head>
<body>
<div>
<input type="text" name="username" id="username-id"/>
</div>
<div>
<input type="text" name="passwd" id="passwd-id"/>
</div>
</body>
</html>
抓取元素:
element = driver.find_element_by_id("passwd-id")
element = driver.find_element_by_name("passwd")
element = driver.find_element_by_tag_name("input")
# 相对路径
element = driver.find_element_by_xpath("//input[@id='passwd-id']")
# 绝对路径
element = driver.find_element_by_xpath("html/body//div[2]/input/")
以上查找都是只返回找到的第一个元素,尽管存在多个重名的元素。
4 操作元素
4.1 填充表单
element.send_keys("要填充的文本")
以上填充,如果文本框已存在内容,将会在保留原内容基础上,在其后继续添加
element.send_keys("要填充的文本", Keys.ARROW_DOWN)
BACKSPACE(或者BACK_SPACE) ——退格、删除键
TAB ——有时可用来切换input框的焦点
ENTER ——回车键,有时可用来代替点击提交按钮
SHIFT(或LEFT_SHIFT) ——和其他按键同时发送,可发送大写字母或特殊符号
CONTROL(或LEFT_CONTROL) ——和其他按键同时发送可实现一些功能如‘CONTROL+A’、‘CONTROL+C’、‘CONTROL+X’、‘CONTROL+V’等等
ALT(或LEFT_ALT) ——和其他键一起使用
SPACE ——输入空格,或选中checkbox、radio框
PAGE_UP/PAGE_DOWN ——通过按键可上下翻页
F1~F12 ——功能键
4.2 清除文本
# 填充文本前,建议清除文本框内容
element.clear()
4.3 选择按钮
element.click() # 模拟鼠标点击
element.submit() # 模拟点击提交按钮
两者略有不同,
click
方法更保险。
submit
方法,WebDriver 会在表单中寻找它所在的表单,如果发现这个元素并没有被表单所包围,那么程序会抛出NoSuchElementException
的异常。
4.4 下拉选项卡
方法1
# 定位到该元素区域
element = driver.find_element_by_xpath("//select[@name='name']")
# element = driver.find_element_by_xpath("//select[@id='id']")
# 找到该元素区域下的所有`option`子元素
all_options = element.find_elements_by_tag_name("option")
# 遍历所有选项
for option in all_options:
print("Value is: %s" % option.get_attribute("value"))
option.click()
方法2
# 导入选择器
from selenium.webdriver.support.ui import Select
element = driver.find_element_by_xpath("//select[@name='name']")
# element = driver.find_element_by_xpath("//select[@id='id']")
select = Select(element)
select.select_by_index(index) # 该索引并不是计数索引,而是html源码设定的值
select.select_by_visible_text("text")
select.select_by_value(value)
x.find_elements_by_*()
可以查找多个重名元素,以列表形式返回
- 取消所有选择
select.deselect_all()
- 查看已选
select.all_selected_options
- 获取所有选项
select.options
5 处理网页内嵌 – frame
网页中内嵌另一个网页,因此在获取网页元素中,需明确告知在哪一个网页中定位该元素!
<html>
<head>
<title>forFrameTest</title>
</head>
<body>
<iframe src='xx.html' id='iframe1' name='iframe1'>
<!---这是另一个网页了,这里面会有<html>,<body>--->
</iframe>
</body>
</html>
定位frame
:
driver.switch_to.frame(reference)
# referencr 可以为index,即计数变量; id; name;driver.find_element_by_tag_name('xx');
可以嵌套定位,也可以返回上一级,甚至最高级;
# 一级一级切入
driver.switch_to.frame('frame1')
driver.switch_to.frame('frame2')
#返回上一级
driver.switch_to.parent_frame()
# 返回主文档
driver.switch_to_default_content()
6 处理弹窗 – alert
弹窗一般是警告、通知等信息
# 获取弹窗
alert = driver.switch_to_alert()
# 打印弹窗信息
print(alert.text)
# 接受或拒绝弹窗内容
alert.accept()
alert.dismiss()
7 等待元素加载
-
sleep()
: 强制等待,设置固定休眠时间。python
的time
包提供了休眠方法sleep()
, 导入time
包后就可以使用sleep()
,进行脚本的执行过程进行休眠。 -
implicitly_wait()
:隐石等待,也叫智能等待,是webdirver
提供的一个超时等待。隐的等待一个元素被发现,或一个命令完成。如果超出了设置时间的则抛出异常。 -
WebDriverWait()
:显示等待,同样也是webdirver
提供的方法。在设置时间内,默认每隔一段时间检测一次当前页面元素是否存在,如果超过设置时间检测不到则抛出异常。默认检测频率为0.5s
,默认抛出异常为:NoSuchElementException
7.1 显式等待
直接在定位元素前设置等待时间
import time
time.sleep(2) # 等待2s
方法2
driver.implicity_wait(2)
# 在2s时间内等待,如果出现直接跳出等待
7.2 复杂方法
WebDriverWait(self,driver,timeout,poll_frequency=POLL_FREQUENCY,ignored_exceptions=None).until(self,method,message=) 或者 WebDriverWait(self,driver,timeout,poll_frequency=POLL_FREQUENCY,ignored_exceptions=None).until_not(self,method,message=) self, 函数本身,在实际使用的时候不需要输入 driver, webdriver的驱动程序,如(IE、FireFox、chrome、safari等) timeout,超时时间,默认以秒为单位 poll_frequency,休眠时间(步长)的间隔,默认为0.5秒,即检测元素是否存在的频率 ignored_exceptions, 超时后的异常信息,默认情况下抛 “NoSuchElementException",大家可以定义忽略的异常信息 WebDriverWait一般由until或until_not配合使用 until(method,message=")调用该方法提供的驱动程序做为一个参数,直到返回值不为False until_not(method,message=")调用该方法提供的驱动程序做为一个参数,直到返回值为False
selenium设置间隔时间(500ms)不断定位该元素,一旦该元素定位成功就执行下一条语句,这在异步框架的网站中很常见
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
driver = webdriver.Chrome()
driver.get("http://somedomain/url_that_delays_loading")
try:
element = WebDriverWait(driver, 10).until(
EC.presence_of_element_located((By.ID, "myDynamicElement"))
)
# element = WebDriverWait(driver,10).until(
#EC.element_to_be_clickable((By.ID,'someid')))
finally:
driver.quit()
方法2
try:
element = webDriverWait(driver, 10, 0.01).until(lambda driver:driver.find_element_by_id('kw'))
---------WebDriverWait(driver,10,1,NoSuchElementException).until(lambda driver:driver.find_element_by_name("d_status"))
8 网页操作
8.1 网页前进和后退
driver.forward()
driver.back()
8.2 网页关闭和退出
driver.close()
driver.quit()
8.3 重新加载页面
driver.refresh()
9 进阶 – Keys
click(on_element=None) ——单击鼠标左键
click_and_hold(on_element=None) ——点击鼠标左键,不松开
context_click(on_element=None) ——点击鼠标右键
double_click(on_element=None) ——双击鼠标左键
drag_and_drop(source, target) ——拖拽到某个元素然后松开
drag_and_drop_by_offset(source, xoffset, yoffset) ——拖拽到某个坐标然后松开
key_down(value, element=None) ——按下某个键盘上的键
key_up(value, element=None) ——松开某个键
move_by_offset(xoffset, yoffset) ——鼠标从当前位置移动到某个坐标
move_to_element(to_element) ——鼠标移动到某个元素
move_to_element_with_offset(to_element, xoffset, yoffset) ——移动到距某个元素(左上角坐标)多少距离的位置
perform() ——执行链中的所有动作
release(on_element=None) ——在某个元素位置松开鼠标左键
send_keys(*keys_to_send) ——发送某个键到当前焦点的元素
send_keys_to_element(element, *keys_to_send) ——发送某个键到指定元素