二.Selenium 元素定位大全
元素的定位是整个Web自动化中的重点以及难点。Selenium实现网页的控制操作主要是通过控制前端的元素来完成,在这个过程中,元素的定位是基础,只有准备抓取到对应元素才能进行后续的自动化控制。
1. 8种基本元素定位
1)id 定位
这是一种最常见的定位方式,假设已知某个元素的id或通过Firebug查找得到id的相关信息,可通过此方法进行定位,比如如下:
python
driver.find_element(By.ID,"findpwd")
2) name 定位
name定位方式将会识别首个name属性等于定位值得页面元素,如果多个元素得name属性都相同,那么可以使用过滤器来进一步细化定位。默认得过滤器类型是value,比如如下:
python
driver.find_element(By.NAME,"username")
3)class_name 定位
HTML 规定使用class来指定元素得类型,class属性在页面中不是唯一的。
实例代码如下:
python
driver.find_element(By.CLASS_NAME,"logindo")
4)tag_name 定位
通过标签的名称来定位元素的位置,这种方法比较困难,因为同一个页面中相同名称的标签往往比较多。
实例代码如下:
python
driver.find_element(By.TAG_NAME,"input")
5)link_text 定位
link_text专门来定位文本链接。
实例代码如下:
python
driver.find_element(By.LINK_TEXT,"忘记密码?")
**注意:**此处的文本最好直接复制页面上的,不建议手动输入,因为手动输入的文本可能会存在部分差异,如空格,中英文符号问题等。
6)partial_link_text 定位
partial_link_text 是link_text的一种补充,有些文本链接较长时,可以提取文本链接的一部分进行定位,只要这一部分信息可以唯一地标识出这个链接。
实例代码如下:
python
driver.find_element(By.PARTIAL_LINK_TEXT,"忘记")
7) Xpath 定位
XPath定位方式由XML和Path两部分构成,以XML格式的树状结构形式进行递归逐级定位。XPath定位的两种方式:绝对路径定位,相对路径定位。
绝对路径:从顶级父标签到当前标签的整个路径结构称为绝对路径。
相对路径:表示相对当前标签而言的路径结构。常用的定位方式有以下几种。
(1) 属性定位语法://标签名@属性名=属性值
注意: 1.标签名可以具体,也可以使用*。2.属性值如果是字符串则需要使用引号。
(2) 使用逻辑运算符可以实现多个属性定位,逻辑运算符有and,or,not。例如,//input@name='uname'and@pwd='upassword',但是一般组合的属性不会超过2个,因为设定的属性越多,对脚本的依赖就越高。
(3) 嵌入函数完成XPath定位。
1)text函数定位语法://标签名text()=对应标签的文本内容。
2)contains函数定位语法://标签名contains(@属性名,对应属性名的前面部分值)。
3)starts-with函数定位语法://标签名starts-with(@属性名,对应属性名的前面部分值)。
4)ends-with函数定位语法://标签ends-with(@属性名,对应属性名的后面部分值)。
**注意:**一般starts-with,ends-with函数能完成定位的,contains函数也能完成,所以在实际工作中contains函数应用的更多。
8)css定位方式
CSS的定位主要是通过选择器来完成的,这属于CSS的高级定位。
CSS定位中选择器的常用语法
|---------|----------|------------------------|
| 选择器 | 示例 | 语法说明 |
| .class | .logindo | 选择class='logindo'的所有元素 |
| #id | #findpwd | 选择id='findpwd'的所有元素 |
| * | * | 选择所有元素 |
| element | p | 选择所有<p>元素 |
1.By定位
具体语法如下:
(1)find_element(By.ID,"kw")
(2)find_element(By.NAME,"wd")
(3)find_element(By.CLASS_NAME,"s_ipt")
(4)find_element(By.TAG_NAME,"input")
(5)find_element(By.LINK_TEXT,u"新闻")
(6)find_element(By.PARTIAL_LINK_TEXT,u"新")
(7)find_element(By.XPATH,"//buttontext()='登录'")
(7)find_element(By.CSS_SELECTOR,"divid="3">h3>a")
**注意:**使用上面这些定位方式的前提是需要导入By类,具体导入语法:from selenium.webdriver.common.by import By。
2.父子定位,二次定位
父子定位:如果当前标签或者子级标签中不存在任何属性可以作为定位方式,则可以查找当前标签的父标签是否存在可定位的属性;如果父级还没有,则可以继续向上一级查找,以此类推,直到查找到可定位的标签。
二次定位:可以先定位到可定位的其中一级标签获取对象,然后再通过该对象作为基准再次定位。
3.JS定位
除了Selenium前面的WebDriver的基本定位方式,还有一些使用基本定位方式无法解决的,如Windows窗口,浏览器滚动条等,这时就需要使用到JS定位。
JS定位实际是使用DOM树的定位方式。DOM树表示树形展示的层级结构,层级结构很好地体现了元素与元素之间的联系。当指出树中所包含的DOM节点时,简单来说就是这个树实现了DOM接口的元素构成,同时这些实现包含了一些其他浏览器内部所需的属性信息。例如:
python
document.getElementById("su")
常用的几种定位方式的总结如下。
(1)id定位:document.getElementById()
(2)name定位:document.getElementByName()
(3)tag定位:document.getElementByTagName()
(4)class定位:document.getElementsByClassName()
(5)CSS定位:document.querySelectorAll()
以上方法都属于document对象的方法,document表示当前HTML页面的对象。
注意:(1)在使用以上方式进行定位时,name,tag,class,CSS定位返回的对象都是复数形式,所以需要通过索引获取具体对象。(2)文本赋值使用的是该方法的value属性,如果是按钮则直接使用click()方法。(3)如果已通过定位元素获取了对应的对象,但是该对象无法直接完成某些事件的操作,则可以通过该对象调用该标签中声明的操作事件的属性值(使用js脚本完成),然后直接使用execute_script执行即可。
4.jQuery 定位
常用的jQuery定位方法有两种:一种使用jQuery选择器来完成元素的选择操作,可以直接获取一个或者一组元素;另外一种就是通过jQuery遍历来选择元素,这种方法常用在获取层级较为复杂的页面元素的情况。
jQuery语法实际是为了HTML元素的选择设置的,不仅可以完成定位,还可以直接对元素完成一些具体的操作,基础语法如下:
python
$(selector).action()
jQuery通过$符号进行定义,selector选择器主要用于获取具体的HTML元素,而action()用于实现对获取的元素的具体操作。
常用的操作如下:
python
$(selector).val('input_value')
$(selector).val('')
$(selector).click()
jQuery常用方法总结:
(1)核心方法
python
$("Element").length #元素的个数,length是属性
$("Element").size() #元素的个数,size()是方法。
$("Element").get() #获取元素在页面中的集合,以数组的形式存储
$("Element").get(index) #index表示第几元素,是数组的下标。
$("Element").get().reverse() #将得到的数组逆序排列
$("Element").index($('Element2')) #获取元素2在元素1中的索引值。
(2)层级元素获取
python
$("Element1 Element2 Element3...") #前面是父级,后面是子集
$("div>p") #获取div元素后面的直接后代p元素
$("div+p") #获取div元素后面的第一个p元素
$("div~p") #获取div元素之后所有同层级的p元素
(3)简单对象获取
python
$("Element:first") #HTML页面中某类元素的第一个元素
$("Element:last") #HTML页面中某类元素的最后一个元素
(4)内容对象的获取和对象可见性
python
$("Element:contains(text)") #获取包含text的元素
(5)子元素的获取
python
$("Element:nth-child(index)") #选择父级下面的第n个元素。
$("Element:first-child") #选择父级下面的最后一个子元素。
$("Element:last-child") #选择父级下面的最后一个子元素。