【DrissionPage】入门指南及查找元素

目录

一、概述

二、特性

2.1 强大的内核

2.2 亮点功能

 三、安装与升级

四、导包与简单示例

4.1 导包

4.2 简单示例

五、查找元素

5.1 概述

5.1.1 在页面中查找

5.1.2 在元素中查找

5.1.3 链式查找

5.1.4 相对查找

5.1.5 shadow root

 5.1.6 简单示例

5.2 基本用法 📌

5.2.1 查找元素的方法

ele()

 eles()

5.2.2 匹配模式 

精确匹配 =

模糊匹配 : 

 匹配开头 ^

匹配结尾 $

5.2.3 查找语法

 id 匹配符 #​

class 匹配符 .​

单属性匹配符 @​

多属性与匹配符 @@​

多属性或匹配符@|​

属性否定匹配符@!​

文本匹配符 text​

文本匹配符 text()​

 @@text()的技巧​

类型匹配符 tag​

css selector 匹配符 css​

 xpath 匹配符 xpath​

selenium 的 loc 元组 📌​

5.2.4 相对定位​

获取父级元素​

🔸 parent()

获取直接子节点​

🔸 child()

🔸 children()

获取后面的同级节点​

🔸 next()

🔸 nexts()

获取前面的同级节点​

🔸 prev()

🔸 prevs()

在后面文档中查找节点​

🔸 after()

🔸 afters()

在前面文档中查找节点​

🔸 before()

🔸 befores()

5.3 更多用法 

5.3.1 静态方式查找元素​

s_ele()​

s_eles()​

5.3.2 获取当前焦点元素​

5.3.3 iframe元素​

 查找 iframe 元素​

在页面下跨级查找​

在 iframe 元素下查找​

5.3.4 ShadowRoot​

5.3.5 等待​

5.4 简化写法

5.4.1 定位符语法简化​

5.4.2 shadow root 简化​

5.4.3 相对定位参数简化​

5.5 找不到元素时 

5.5.1 默认情况​

5.5.2 立即抛出异常​

5.5.3 设置默认返回值​

5.6 语法速查表

5.6.1 定位语法​

基本用法​

 组合用法​

简化写法​

5.6.2 相对定位​

5.6.3 其它​


一、概述

DrissionPage 是一个基于 python 的网页自动化工具。

它既能控制浏览器,也能收发数据包,还能把两者合而为一。

可兼顾浏览器自动化的便利性和 requests 的高效率。

它功能强大,内置无数人性化设计和便捷功能。

它的语法简洁而优雅,代码量少,对新手友好。

二、特性

2.1 强大的内核

本库采用全自研的内核,内置了 N 多实用功能,对常用功能作了整合和优化,对比 selenium,有以下优点:

  • 无 webdriver 特征
  • 无需为不同版本的浏览器下载不同的驱动
  • 运行速度更快
  • 可以跨 iframe 查找元素,无需切入切出
  • 把 iframe 看作普通元素,获取后可直接在其中查找元素,逻辑更清晰
  • 可以同时操作浏览器中的多个标签页,即使标签页为非激活状态,无需切换
  • 可以直接读取浏览器缓存来保存图片,无需用 GUI 点击另存
  • 可以对整个网页截图,包括视口外的部分(90以上版本浏览器支持)
  • 可处理非open状态的 shadow-root

2.2 亮点功能

  • 极简的语法规则。集成大量常用功能,代码更优雅
  • 定位元素更加容易,功能更强大稳定
  • 无处不在的等待和自动重试功能。使不稳定的网络变得易于控制,程序更稳定,编写更省心
  • 提供强大的下载工具。操作浏览器时也能享受快捷可靠的下载功能
  • 允许反复使用已经打开的浏览器。无需每次运行从头启动浏览器,调试超方便
  • 使用 ini 文件保存常用配置,自动调用,提供便捷的设置,远离繁杂的配置项
  • 内置 lxml 作为解析引擎,解析速度成几个数量级提升
  • 使用 POM 模式封装,可直接用于测试,便于扩展
  • 高度集成的便利功能,从每个细节中体现

 三、安装与升级

# 安装
pip install DrissionPage

# 升级
pip install DrissionPage --upgrade

# 升级指定版本
pip install DrissionPage==4.0.0b17

四、导包与简单示例

4.1 导包

# 如果只要控制浏览器,导入ChromiumPage。
from DrissionPage import ChromiumPage

# 如果只要收发数据包,导入SessionPage。
from DrissionPage import SessionPage

# WebPage是功能最全面的页面类,既可控制浏览器,也可收发数据包。
from DrissionPage import WebPage

4.2 简单示例

from DrissionPage import ChromiumPage

# 导入
from DrissionPage import ChromiumPage

# 创建对象
page = ChromiumPage()
# 访问网页
page.get('https://www.baidu.com')
# 输入文本
page('#kw').input('DrissionPage')
# 点击按钮
page('#su').click()
# 等待页面跳转
page.wait.load_start()
# 获取所有结果
links = page.eles('tag:h3')
# 遍历并打印结果
for link in links:
    print(link.text)

五、查找元素

5.1 概述

本库提供一套简洁易用的语法,用于快速定位元素,并且内置等待功能、支持链式查找,减少了代码的复杂性。

同时也兼容 css selector、xpath、selenium 原生的 loc 元组。

定位元素大致分为三种方法:

  • 在页面或元素内查找子元素
  • 根据 DOM 结构相对定位
  • 根据页面布局位置相对定位

使用方式

所有页面对象和元素对象,都可以在自己内部查找元素,元素对象还能以自己为基准,相对定位其它元素。

页面对象包括:SessionPageChromiumPageChromiumTabChromiumFrameWebPageWebPageTab

元素对象包括:SessionElementChromiumElementShadowRoot

5.1.1 在页面中查找

使用页面对象的ele()eles()方法,获取页面内指定元素对象。

from DrissionPage import SessionPage

page = SessionPage()
page.get('https://www.baidu.com')
ele = page.ele('#su')

5.1.2 在元素中查找

使用元素对象的ele()eles()child()children()方法,获取元素内指定后代元素对象。

ele1 = page.ele('#s_fm')
ele2 = ele1.ele('#su')

son = ele1.child('tag:div')  # 获取第一个直接div子元素
sons = ele1.children('tag:div')  # 获取所有直接div子元素

5.1.3 链式查找

因为对象本身又可以查找对象,所有支持链式操作,上面两个例子可合并为:

ele = page.ele('#s_fm').ele('#su')

5.1.4 相对查找

元素对象在以自己为基准,执行相对查找。

ele = page.ele('#su')

parent = ele.parent(2)  # 获取ele元素的第二层父元素
brother = ele.next('tag:a')  # 获取ele元素后面的第一个a元素
after = ele.after('tag:div')  # 获取ele后面文档中第一个div元素

5.1.5 shadow root

使用浏览器元素对象的shadow_root属性获取该元素下的ShadowRoot对象。

shadow = page.ele('#ele1').shadow_root

在 shadow root 元素中搜索方法与普通元素一致。

shadow = page.ele('#ele1').shadow_root
ele = shadow.ele('#ele2')

 5.1.6 简单示例

<html>
<body>
<div id="one">
    <p class="p_cls" name="row1">第一行</p>
    <p class="p_cls" name="row2">第二行</p>
    <p class="p_cls">第三行</p>
</div>
<div id="two">
    第二个div
</div>
</body>
</html> id="su" class="btn self-btn bg s_btn">

我们可以用页面对象去获取其中的元素: 

# 获取 id 为 one 的元素
div1 = page.ele('#one')

# 获取 name 属性为 row1 的元素
p1 = page.ele('@name=row1')

# 获取包含“第二个div”文本的元素
div2 = page.ele('第二个div')

# 获取所有div元素
div_list = page.eles('tag:div')

也可以获取到一个元素,然后在它里面或周围查找元素:

# 获取到一个元素div1
div1 = page.ele('#one')

# 在div1内查找所有p元素
p_list = div1.eles('tag:p')

# 获取div1后面一个元素
div2 = div1.next()

5.2 基本用法 📌

5.2.1 查找元素的方法

ele()

页面对象和元素对象都拥有此方法,用于查找其内部的一个条件匹配的元素。

页面对象和元素对象的ele()方法参数名称稍有不同,但用法一样。

SessionPageChromiumPage获取元素的方法是一致的,但前者返回的元素对象为SessionElement,后者是ChromiumElement

参数名称 类型 默认值 说明
locator
(元素对象)
str
Tuple[str, str]
必填 元素的定位信息。可以是查询字符串,或 loc 元组
locator
(页面对象)
str
SessionElement
Tuple[str, str]
必填 元素的定位信息。可以是查询字符串、loc 元组或一个SessionElement对象
index int 1 获取第几个匹配的元素,从1开始,可输入负数表示从后面开始数
timeout float None 等待元素出现的超时时间,为None使用页面对象设置,SessionPage中无效
返回类型 说明
SessionElement SessionPageSessionElement查找到的第一个符合条件的元素对象
ChromiumElement 浏览器页面对象或元素对象查找到的第一个符合条件的元素对象
ChromiumFrame 当结果是框架元素时,会返回ChromiumFrame,但 IDE 中不会包含该提示
NoneElement 未找到符合条件的元素时返回

说明

  • loc 元组是指 selenium 定位符,例:(By.ID, 'XXXXX')。下同。
  • ele('xxxx', index=2)eles('xxxx')[1]结果一样,不过前者会快很多。

示例:

from DrissionPage import SessionPage

page = SessionPage()

# 在页面内查找元素
ele1 = page.ele('#one')

# 在元素内查找后代元素
ele2 = ele1.ele('第二行')
 eles()

此方法与ele()相似,但返回的是匹配到的所有元素组成的列表。

页面对象和元素对象都可调用这个方法。

eles()返回的是普通列表,链式操作需加下标,如page.eles('...')[0].ele('...')

参数名称 类型 默认值 说明
locator str
Tuple[str, str]
必填 元素的定位信息,可以是查询字符串,或 loc 元组
timeout float None 等待元素出现的超时时间,为None使用页面对象设置,SessionPage中无效
返回类型 说明
List[SessionElement] SessionPageSessionElement找到的所有元素组成的列表
List[ChromiumElement, ChromiumFrame] 浏览器页面对象或元素对象找到的所有元素组成的列表

示例:

# 获取页面内的所有p元素
p_eles = page.eles('tag:p')

# 获取ele1元素内的所有p元素
p_eles = ele1.eles('tag:p')

# 打印第一个p元素的文本
print(p_eles[0])

5.2.2 匹配模式 

精确匹配 =

表示精确匹配,匹配完全符合的文本或属性。

# 获取name属性为'row1'的元素
ele = page.ele('@name=row1')
模糊匹配 : 

表示模糊匹配,匹配含有指定字符串的文本或属性。

# 获取name属性包含'row1'的元素
ele = page.ele('@name:row1')
 匹配开头 ^

表示匹配开头,匹配开头为指定字符串的文本或属性。

# 获取name属性以'row1'开头的元素
ele = page.ele('@name^ro')
匹配结尾 $

表示匹配结尾,匹配结尾为指定字符串的文本或属性。

# 获取name属性以'w1'结尾的元素
ele = page.ele('@name$w1')

5.2.3 查找语法

 id 匹配符 #

表示id属性,只在语句最前面且单独使用时生效,可配合匹配模式使用。

# 在页面中查找id属性为one的元素
ele1 = page.ele('#one')

# 在ele1元素内查找id属性包含ne文本的元素
ele2 = ele1.ele('#:ne')  


class 匹配符 .

表示class属性,只在语句最前面且单独使用时生效,可配合匹配模式使用。

# 查找class属性为p_cls的元素
ele2 = ele1.ele('.p_cls')

# 查找class属性'_cls'文本开头的元素
ele2 = ele1.ele('.^_cls')  

因为只加 . 时默认是精确匹配元素属性 class,所以如果某元素有多个类名,必须写 class 属性的完整值(类名的顺序也不能变)。如果需要只匹配多个类名中的一个,可以使用模糊匹配符 :

# 精确查找class属性为`p_cls1 p_cls2 `的元素
ele2 = ele1.ele('.p_cls1 p_cls2 ')

# 模糊查找class属性含有类名 'p_cls2' 的元素
ele2 = ele1.ele('.:p_cls2')  

若仍需要更复杂的匹配方式,请使用多属性匹配符。


单属性匹配符 @

表示某个属性,只匹配一个属性。

@关键字只有一个简单功能,就是匹配@后面的内容,不再对后面的字符串进行解析。因此即使后面的字符串也存在@@@ ,也作为要匹配的内容对待。所以只要是多属性匹配,包括第一个属性在内的所有属性都必须用@@开头。

注意

如果属性中包含特殊字符(如包含@),用这个方式不能正确匹配到,需使用 css selector 方式查找。且特殊字符要用\转义。

# 查找name属性为row1的元素
ele2 = ele1.ele('@name=row1')

# 查找name属性包含row文本的元素
ele2 = ele1.ele('@name:row')

# 查找name属性以row开头的元素
ele2 = ele1.ele('@name^row')

# 查找有name属性的元素
ele2 = ele1.ele('@name')

# 查找没有任何属性的元素
ele2 = ele1.ele('@')

# 查找email属性为abc@def.com的元素,有多个@也不会重复处理
ele2 = ele1.ele('@email=abc@def.com')

# 属性中有特殊字符的情形,匹配abc@def属性等于v的元素
ele2 = ele1.ele('css:div[abc\@def="v"]')


多属性与匹配符 @@

匹配同时符合多个条件的元素时使用,每个条件前面添加@@作为开头。

注意

  • 匹配文本或属性中出现@@@|@!时,不能使用多属性匹配,需改用 xpath 的方式。
  • 如果属性中包含特殊字符(如包含@),用这个方式不能正确匹配到,需使用 css selector 方式查找。且特殊字符要用\转义。
# 查找name属性为row1且class属性包含cls文本的元素
ele2 = ele1.ele('@@name=row1@@class:cls')

@@可以与下文介绍的tag配合使用:

ele = page.ele('tag:div@@class=p_cls@@name=row1')


多属性或匹配符
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

春天的菠菜

一毛两毛也是动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值