​ 我们在做WEB自动化时,最根本的就是操作页面上的各种元素,而操作的基础便是元素的定位,只有准确地定位到唯一元素才能进行后续的自动化控制,下面将对各种元素定位方式进行总结归纳。

​ 说明:以下操作统一使用百度首页<www.baidu.com>进行示例,鼠标右键然后点击检查(或按f12)可以查看具体的前端代码。

单一属性定位

​ 6种单一属性定位 : id,name,class name,tag name,link,partial_link

2种多样式定位:css、xpath(强烈推荐)

通过元素的id

# 通过id(id唯一)
ele = driver.find_element_by_id("kw") # 类 WebElement - 属性、方法
print(ele.get_attribute('class')) # 获取该id的class属性值
ele.send_keys("selenium") # 发送内容

​ 在前端页面中,id是指页面匀速的的属性名id值,元素的id值在当前整个HTML页面中是唯一的,因此可以通过id属性来唯一定位一个元素,是首选的元素定位方式,但不是每个元素都有id属性。此外,也有动态变化的id值,即每次进入页面该元素的id值都不一样,一般是由一串英文+数字组成的字符串,这种情况下就不要使用id去定位元素了(因为下一次很有可能就找不到它了)。

通过元素的name

# 通过name
driver.find_element_by_name("wd") # 不一定唯一 # elements

​ 元素的name属性,但name不一定是唯一的,就像大家的身份证号是唯一的,但是名字会有重复。driver.find_element_by_name只返回第一个匹配到的元素,如果想返回所有匹配到该name的元素,则使用driver.find_elements_by_name,区别就是element带不带s。这里特别说明一下,find_elements不管找到多少个,都会返回 一个list(找不到则返回空列表),列表当中的每一个元素就是一个 WebElement。

通过元素的class

# 通过class_name
driver.find_element_by_class_name('mnav c-font-normal c-color-t') # 不一定唯一,只返回匹配到的第一个元素
driver.find_elements_by_class_name('mnav c-font-normal c-color-t') # 返回元素列表,按照dom树从上往下

​ 元素的class属性,在前端,class一般是用来元素进行分组的,并对这一级元素设置相同的样式,因此会存在多个元素会共用一个class,不一定是唯一值。与name一样,elements时返回匹配到的元素列表。

通过元素的标签名

# 通过tag_name
driver.find_element_by_tag_name('span') # 不唯一 # elements

​ tag就是元素的标签标识,不一定是唯一值,elements时返回匹配到的元素列表。

通过元素的超链接文本

# 通过link_text
driver.find_element_by_link_text('hao123') # 不是唯一 # elements

​ 精确匹配链接的文本值,不一定是唯一值,elements时返回匹配到的元素列表。

通过元素的部分超链接文本

# 通过partial_link_text
driver.find_element_by_partial_link_text('hao') # 不是唯一 # elements

​ 模糊匹配链接的文本值,elements时返回匹配到的元素列表。

XPTH定位

​ 以上介绍的6中定位方式,都是针对元素的单一特征来定位元素,但在实际应用中,一般都需要组合以上各种情况来定位一个元素。那么xpath和css定位就可以实现各种组合,基本可以覆盖所有的元素定位。

​ xpath是一门在xml文档中查找信息的语言,因为html与xml比较相似,用得比较广泛,所以xpath也可以用于在html对元素进行定位。它是将整个html看成一个树形结构,html为根节点,页面当中节点与其他节点可以有祖先、父辈、兄弟、这样的关系,类似一个族谱。

​ selenium提供的xpath定位的方法名:find_element_by_xpath(xpath表达式),表达式语法如下:

表达式 说明
/ 绝对定位,从根节点选取
// 相对定位,选择匹配的节点
. 选择当前节点
.. 选择当前节点的父节点
@ 选择属性,如:@class="class值",@id="id值",属性放在中括号[]中
* 通配符,匹配所有
@* 通配符,匹配所有属性,如:@*="test"
  • 绝对定位(不建议) : /单斜杠开头,严格按照层级、同级元素的位置,只要位置改变就无法定位,如:/html/body/div[2]/[form]/div[1]/input
  • 相对定位://双斜杠开头 ,在参照物之下只要符合条件的元素存在即可,表达式://标签名[@属性名=值] ,用*表示要匹配所有标签 ,如://*[@id="kw"] 匹配所有标签
  • 下标定位(不建议):路径下相同标签的下标,如://*[@id="th"]/a[2],意思是该路径下第二个a标签
  • 逻辑运算:表达式中可以使用and 、or 描述元素的多个属性,表达式://标签名[@属性名=值 and @属性名=值]
  • 层级定位:靠本身特性无法唯一定位的时候,使用层级去定位,如://div[@id="u1"]//a[@name="tj_login"]。/(单斜杠)表示在前一个元素的直系下, //(双斜杠)表示在前个元素之下的所有范围内
  • 文本定位: 通过标签内的文本内容,表达式: //标签名[text()="文本"]
  • 包含(部分属性):标签的部分属性,表达式://标签名[contains(@属性名 , "部分属性值")] ,如: //a[contains(@href,"Cource/homework")],部分文本也可以,//a[contains(text(), "部分文本")]
  • 轴定位:一般用于表格样式的数据列,需要通过组合来进行定位,轴运算名称为以下6种,使用语法:/轴名称::节点名称[@属性=值],例: //div//table//td/preceding::td,只要后面接的是轴定位要用/(单斜杠)。
    • ancestor:祖先节点,父
    • parent:父节点
    • preceding:当前元素节点标签之前的所有节点(html页面先后顺序)
    • preceding-sibling:当前元素节点标签之前的所有兄弟节点
    • following:当前元素节点标签之后的所有节点(html页面先后顺序)
    • following-sibling:当前元素节点标签之后的所有兄弟节点
from selenium import webdriver
import time driver = webdriver.Chrome()
driver.get("https://www.baidu.com") # 定位到输入框并输入搜索内容
driver.find_element_by_xpath("//input[@id='kw']").send_keys("selenium")
# 定位到百度按钮,并点击
driver.find_element_by_xpath("//input[@class='btn self-btn bg s_btn']").click()
time.sleep(5) # 关闭浏览器
driver.quit()

CSS定位

​ css定位也可以较为灵活地选择控件的任意属性,一般情况下定位速度要比xpath要快,但比较复杂,这里只做简单介绍。有兴趣的可以深入了解。

选择器 例子 描述
class .intro class选择器,选择class="intro"的所有元素
#id #firstname id选择器,选择id= " firstname"的所有元素
* * 选择所有元素
element p 元素所有<p>元素
element > element div > input 选择父元素为<div>的所有<input> 元素
element + element div + input 选择同一级中紧接在<div> 元素之后的所有<input> 元素
[attribute= value] [target=_blank] 选择target="_blank"的所有元素。

​ 以百度输入框和搜索框为例:

  • find_element_by_css_selector(".s_ipt") #通过class属性定位
  • find_element_by_css_selector("#kw") #通过id属性
  • find_element_by_css_selector("input") #通过标签名
  • find_element_by_css_selector("span>input") #通过父子关系定位,查找span所有标签名叫input的子元素
  • find_element_by_css_selector("[name='kw']") #通过属性定位
  • find_element_by_css_selector("span.bg s_ipt_wr>input.s_ipt") #组合定位,父元素是span标签名,class属性是.bg s_ipt_wr,有一个子元素,标签名为input,class属性是s_ipt

辅助定位工具

​ 快捷键f12调出浏览器的开发者工具 —— elements,或通过右击检查调出,以chrome浏览器为例,如下图,点击左上角箭头,再用鼠标点击页面中想要定位的元素,该元素所在代码行会高亮显示,crtl + f可以调出元素查找框,输入表达式,在输入框右边可以看到该表达式定位的元素是否存在且唯一,可以通过组合定位或者更换更具代表性的属性去保证定位到的元素是唯一的。

​ 在上图的底部(搜索框对上一栏),选中元素后还可以看到元素的路径,可以用此判断元素是否在iframe表单中;而如果不确定元素是否在html里,可以利用字符串的元素查找,代码如下:

test = driver.page_source.find("<p>hello</p>")
print(test) # 返回-1就是不存在

【python+selenium的web自动化】- 8种元素定位方式详解的更多相关文章

  1. Python selenium —— 父子、兄弟、相邻节点定位方式详解

    今天跟大家分享下selenium中根据父子.兄弟.相邻节点定位的方法,很多人在实际应用中会遇到想定位的节点无法直接定位,需要通过附近节点来相对定位的问题,但从父节点定位子节点容易,从子节点定位父节点. ...

  2. 【Selenium01篇】python+selenium实现Web自动化:搭建环境,Selenium原理,定位元素以及浏览器常规操作!

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 二.话不多说,直接开干,开始搭建自动化测试环境 这里以前在 ...

  3. 【Selenium05篇】python+selenium实现Web自动化:读取ini配置文件,元素封装,代码封装,异常处理,兼容多浏览器执行

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第五篇博 ...

  4. 【Selenium03篇】python+selenium实现Web自动化:元素三类等待,多窗口切换,警告框处理,下拉框选择

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第三篇博 ...

  5. 【Selenium02篇】python+selenium实现Web自动化:鼠标操作和键盘操作!

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第二篇博 ...

  6. 【Selenium06篇】python+selenium实现Web自动化:日志处理

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第六篇博 ...

  7. 【Selenium04篇】python+selenium实现Web自动化:文件上传,Cookie操作,调用 JavaScript,窗口截图

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第四篇博 ...

  8. 【Selenium07篇】python+selenium实现Web自动化:PO模型,PageObject模式!

    一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第七篇博 ...

  9. JAVA中的四种JSON解析方式详解

    JAVA中的四种JSON解析方式详解 我们在日常开发中少不了和JSON数据打交道,那么我们来看看JAVA中常用的JSON解析方式. 1.JSON官方 脱离框架使用 2.GSON 3.FastJSON ...

随机推荐

  1. Beautiful numbers CodeForces - 55D

    题意: 找出区间[li,ri]内有多少数满足,这个数的每一个位的非0数都能把这个数整除 题解: 因为这个数每一位的值都可以把这个数整除,那也就是说这个数是它所有位数的公倍数,但是可能不是最小公倍数. ...

  2. Educational Codeforces Round 91 (Rated for Div. 2) A. Three Indices (模拟)

    题意:有一长度为\(n\)的序列,问是否能找到\(a_{i}<a_{j},a_{j}>a_{k},(i<j<k)\),如果满足,输出其位置. 题解:直接暴力两头找即可,最坏复杂 ...

  3. 3.PowerShell DSC核心概念

    PowerShell DSC有三个核心概念 配置 配置是声明性的PowerShell 脚本,用于定义和配置资源实例. DSC 配置是幂等的. 资源 资源是 DSC 的"实现器"部分 ...

  4. redis持久化-AOF

    1.aof文件写入与同步 2.aof重写 重写的目的是为了减小aof文件的体积,redis服务器可以创建一个新的aof文件来代替现有的aof文件,新文件不会有冗余的命令. BGREWRITEAOF:遍 ...

  5. os-hackNOS-2(wp5.3本地文件包含 rbash绕过)

    一.信息收集 直接netdiscover,找到IP是 192.168.56.101 然后端口扫描一波 只打开了22和80端口,访问一下80端口,是apache首页,那就继续查目录赛.,发现了一个tsw ...

  6. 解决debian (Friendly ARM 嵌入式板)的sudo等一部分命令无法TAB补全

    TAB对于比较长的命令在使用时是十分方便的,最近就遇到TAB 键无法补全sudo后跟的命令的情况因此去网上取经.在一篇博客中找到解决问题的方法,觉得大牛们写的太精炼然后自己做如下总结方便自已以后解决类 ...

  7. CSS 滚动条宽度 All In One

    CSS 滚动条宽度 All In One 滚动条宽度 IE 16px Chrome 12px scrollbar width bug 改变设计稿的宽度,没考虑到 scrollbar width sol ...

  8. CSS 弹性盒子模型

    CSS 弹性盒子模型 https://www.w3.org/TR/2016/CR-css-flexbox-1-20160526/ CSS Flexible Box Layout Module Leve ...

  9. iPhone 12 Pro 屏幕时间设置的密码锁出现弹窗 UI 错位重大 Bug

    iPhone 12 Pro 屏幕时间设置的密码锁出现弹窗 UI 错位重大 Bug iOS 14.1 Bug 弹窗 UI 非常丑 弹窗屏占太高了 屏幕使用时间 https://support.apple ...

  10. ES2021 & ES12

    ES2021 & ES12 ES2021 new features replaceAll String.prototype.replaceAll const str = `abc,abc`; ...