python爬虫之selenium库



selenium库

selenium库是模拟浏览器,动态爬虫的一个库。首次使用需要安装

pip install selenium

安装之后导入selenium包就可以了。

import selenium

一般常用的类有:

from selenium import webdriver  # 引擎
from selenium.webdriver.common.keys import Keys  # 键盘操作,回车、方向键等等
from selenium.webdriver.common.by import By    # 定位元素使用的
from selenium.webdriver.support.ui import WebDriverWait   # 显性等待
from selenium.webdriver.support import expected_conditions as EC  # 显性等待需要的参数

下面从引擎开始学习



引擎启动器

引擎相当于是,浏览器启动器,可以打开谷歌、火狐、PhantomJS(无界面浏览器)。要启动引擎,本地需要下载对应的浏览器,比如说,你想使用

driver = webdriver.Firefox()

你就必须下载火狐浏览器才可以启动引擎。

可能会出现下载完之后还是打不开火狐浏览器的情况,这是因为selenium和火狐的版本不一致导致的,需要下载一个geckodriver,放到某一个环境路径中,比如python的环境变量。将可执行文件放到里面就可以正常启动了。资源可以在我的博客中找到。

现在就打开一个引擎了,接下来访问网址url。



访问地址

访问网址非常简单。

url = 'http://www.baidu.com'
driver.get(url)

就可以了。当然还可以添加请求头,cookie,等等。在这里就不说了,因为自己现在还没有遇到需要加请求头的网站(主要是自己不会hhhh)。



切换网页,框架

有时会打开多个网页,这时可能,需要切换网页。

driver.window_handles  # 会返回所有打开的网页名字
driver.switch_to_window('网页名字')

当你需要,在上一次点击之前网站,也就是网页的后退。可以使用

driver.forward()     #前进
driver.back()        # 后退

当然一个网页可能有不同的框架组成,定位元素时,需要切换框架才可以定位成功,这时就需要:

driver.switch_to_frame('框架的name或者id')

# 当一个框架没有name或者id属性时,可以使用以下方法:
rq = driver.find_element_by_xpath('//iframe[@scrolling="no"]')  # 先定位,后切换
driver.switch_to.frame(rq)

# 跳出当前框架,返回到上一个框架
driver.switch_to.parent_frame()  

# 跳到最开始的框架。



定位元素

定位元素是selenium中最重要的,因为很多操作都是对元素进行的,所以你得先找到需要操作的元素,才能继续进行。

定位元素有很多方法,其中有常用的有:

driver.find_element_by_id()   # 通过id查找
driver.find_element_by_class_name()  # 通过class查找
driver.find_element_by_xpath()    # 根据符合xpath语法的元素查找
driver.find_element_by_link_text()  # 根据完全符合文本的元素查找
driver.find_element_by_partial_link_text()  # 根据包括文本的元素查找
# 返回一个元素对象,可以继续使用上面的查找方法。
# 例如driver.find_element_by_link_text('新语音呼入报表').find_element_by_id('data')

# 上面的都是找到一个符合条件的元素,就返回。在element加一个s就是找出所有符合条件的元素。
driver.find_elements_by_id()
driver.find_elements_by_class_name()
driver.find_elements_by_xpath()
driver.find_elements_by_link_text()
driver.find_elements_by_partial_link_text()

# element如果没有找到符合条件的元素,会返回一个异常。
# elements如果没有找到符合条件的元素,会返回一个空列表

当然还有暂时我用的不多的定位方法,比如:

driver.find_element_by_css_selector()  # 根据css语法定位
driver.find_element_by_tag_name()  # 根据标签名定位元素
driver.find_element_by_name()   # 通过name这个属性定位?

还有一个总方法:

driver.find_element(by.ID,'data')  # 通过id值查询
driver.find_elements(by.ID,'data')  # 通过id值查询
# 这个需要使用by.(需要定位类型),结果和上面的一样。



对元素进行操作

我们现在已经定位到了一个元素了,比如:

el = driver.driver.find_element_by_id('starttime')

现在可以对这个元素进行以下常用操作:

el.click()  # 点击
el.clear()  # 清空值
el.send_keys('123') # 将123添加到el元素中

当然还有其他的鼠标操作:

#导入 ActionChains 类
from selenium.webdriver import ActionChains

# 鼠标移动到 ac 位置
ac = driver.find_element_by_xpath('element')
ActionChains(driver).move_to_element(ac).perform()

# 在 ac 位置单击
ac = driver.find_element_by_xpath("elementA")
ActionChains(driver).move_to_element(ac).click(ac).perform()

# 在 ac 位置双击
ac = driver.find_element_by_xpath("elementB")
ActionChains(driver).move_to_element(ac).double_click(ac).perform()

# 在 ac 位置右击
ac = driver.find_element_by_xpath("elementC")
ActionChains(driver).move_to_element(ac).context_click(ac).perform()

# 在 ac 位置左键单击hold住,点住不动
ac = driver.find_element_by_xpath('elementF')
ActionChains(driver).move_to_element(ac).click_and_hold(ac).perform()

# 将 ac1 拖拽到 ac2 位置
ac1 = driver.find_element_by_xpath('elementD')
ac2 = driver.find_element_by_xpath('elementE')
ActionChains(driver).drag_and_drop(ac1, ac2).perform()



网页等待、元素等待、元素遮蔽

有时会因为网页没有加载完成,导致元素查找不到,所以需要等一下,有三种等待,

1、显性等待

显示等待,就是等某个元素加载出来之后,再进行提取。

# WebDriverWait 库,负责循环等待
from selenium.webdriver.support.ui import WebDriverWait
# expected_conditions 类,负责条件出发
from selenium.webdriver.support import expected_conditions as EC

# 每隔10秒查找页面元素 id="myDynamicElement",直到出现则返回
WebDriverWait(driver, 10).until(EC.presence_of_element_located((By.ID, "myDynamicElement")))

如果不写参数,程序默认会 0.5s 调用一次来查看元素是否已经生成,如果本来元素就是存在的,那么会立即返回。

2、隐形等待

隐式等待比较简单,就是简单地设置一个等待时间,单位为秒。

driver.implicitly_wait(10) # seconds,等待10秒,知道界面加载完成

3、暴力等待

直接使用sleep()等待,不推荐使用

import time
time.sleep(2) # 程序暂停2秒

有时元素也加载出来,但是被另一个元素遮蔽了,这时需要等待遮蔽的元素消失,再去提取元素。例如:

obscures = driver.find_elements_by_xpath('//div[@id="1E37CE2C72950001AC1115D0A939F360"]')
# obscures遮蔽元素
if obscures != []:
	WebDriverWait(driver, 10).until(EC.invisibility_of_element(obscures[0]))
    # 等待遮蔽元素消失



网页转换、Beautifulsoup、lxml

当我们已经进到所需要数据的网页了,这时,需要将它driver.page_source进行转化为xml文档或者html文档,进而使用BeautifulSoup、xpath进行提取数据。

soup = BeautifulSoup(driver.page_source,'xml')
# 转化为beautifulsoup格式,使用beautifulsoup语法,提取数据。

html = etree.HTML(driver.page_source)
# 转化为xml文档,使用xpath语法,提取数据


网页关闭,引擎退出

拿到想要的数据之后,将引擎关闭。

driver.quit()


定位元素的一些注意事项

想要代码稳定,定位元素时,尽量选择这个元素唯一的值,id、class、文本,等等,有时id、class也不太稳定,那就选择文本;这一个子标签可能没有,那就查找上一级;实在不行就使用elements,判断一下是不是空列表,然后再进行提取。尽量保证百分比可以提取到元素,这样后面的代码,才可以更稳定。



其他数据保存的问题(简略介绍,以后会详细学习)

有一个需求是,保留excel的格式,只填入数据,可以使用以下方法:

import pandas as pd
from openpyxl import load_workbook

s = pd.DataFrame('要保存的数据')

#读取被写入的Excel工作簿
book = load_workbook('test.xlsx')
#建立写入对象
write = pd.ExcelWriter(r'test.xlsx', engine='openpyxl')
write.book = book
write.sheets = {ws.title: ws for ws in book.worksheets}
#写入数据
s.to_excel(write, sheet_name='分时话务量统计', header=False, index=False, startrow=3, startcol=21)
write.save()
write.close()

网页弹窗、填充表单、模拟滚动条滚动,之后再学习。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

努力生活的黄先生

你的鼓励将是我创作的最大动力

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

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

打赏作者

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

抵扣说明:

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

余额充值