文章目录
安装配置教程自行搜索
所用驱动chromedriver应与chrome浏览器版本相对应
pip install selenium
笔者selenium所用版本为4.11.2,新旧版之间会有差别
from selenium import webdriver
driver = webdriver.Chrome()
实例化driver对象后,driver对象有一些常用的属性和方法
driver.page_source #当前标签页浏览器渲染之后的网页源代码
driver.current_url #当前标签页的url
driver.close()#关闭当前标签页,如果只有一个标签页则关闭整个浏览器
driver.quit()#关闭浏览器
driver.forward()#页面前进
driver.back()#页面后退
driver.refrash()#页面刷新
driver.save_screenshot("img_name")#页面截图
我们使用Selenium时会觉得浏览器加载很慢,这和它的页面加载策略有关
Selenium的页面加载策略(pageLoadStrategy)
本段摘自:https://blog.csdn.net/momoda118/article/details/120624777
- normal:等待整个页面加载完毕再开始执行操作(默认为此)
- eager:等待整个dom树加载完成,即DOMContentLoaded这个事件完成,也就是只要 HTML完全加载和解析完毕就开始执行操作。放弃等待图片、样式、子帧的加载。
- none:等待html下载完成,哪怕还没开始解析就开始执行操作。
加载策略设置为eager
配置代码如下:
chrome_options = Options()
chrome_options.page_load_strategy ='eager'
driver = webdriver.Chrome(options=chrome_options)
加载策略设置为none
加载策略设置为none,并引入retry做重试(目的是为了防止报错,当然设置隐式等待也可,但没retry稳妥)可以只用2s左右就能执行完成,完整代码如下:
import datetime
from retrying import retry # 需第三方库,需pip进行安装from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By
@retry(wait_fixed=10, stop_max_attempt_number=1)defclick(path):
driver.find_element(By.XPATH, path).click()
chrome_options = Options()
chrome_options.page_load_strategy ='none'
driver = webdriver.Chrome(options=chrome_options)
start_time = datetime.datetime.now()
driver.get('https://www.iqiyi.com/')
click('//*[@id="block-C"]/div/div/div/div[1]/div[1]/div/div[1]/div/div/a/span[2]')
end_time = datetime.datetime.now()print(end_time - start_time)
元素定位
本段参考:https://blog.csdn.net/qq_18298049/article/details/117136214
element = driver.find_element(By.ID,'kw')# 通过ID定位搜索框
element = driver.find_element(By.NAME,'wd')# 通过name定位搜索框
element = driver.find_element(By.CLASS_NAME,'s_ipt')# 获取百度首页搜索框
element = driver.find_element(By.TAG_NAME,'input')# 查找标签名称是input的元素
element = driver.find_element(By.LINK_TEXT,'贴吧')# 定位贴吧
element = driver.find_element(By.PARTIAL_LINK_TEXT,'贴')# 定位贴吧
头尾匹配写法:其中,头尾匹配可以是部分字符,部分匹配需要是按空格分隔的完整字符。
条件htmlvalues 写法1 (头部匹配)values 写法2 (尾部匹配)values 写法3 (部分匹配)class< button class=“el-button el-button–primary”>‘[class^=“el-button”]’‘[class$=“–primary”]’‘[class~=“el-button”]’
css selector
element = driver.find_element(By.CSS_SELECTOR,'#kw')# #kw id选择器
element = driver.find_element(By.CSS_SELECTOR,'.s_ipt')# .s_ipt class选择器
element = driver.find_element(By.CSS_SELECTOR,'form #kw')# 后代元素选择器
element = driver.find_element(By.CSS_SELECTOR,"input[name='wd']")# 属性值定位选择器# 同时包含两个条件# 包含type='text'与maxlength='50'两个条件的元素,语法上不需要and进行连接
driver.find_element(By.CSS_SELECTOR,'[type="text"][maxlength="50"]')# 包含一个条件且不包含另一条件# 包含type='text'且不包含maxlength='50'的元素,语法上使用:not()进行连接
driver.find_element(By.CSS_SELECTOR,'[type="text"]:not([maxlength="50"])')
xpath
相对路径
//#查找页面根元素//input#查找页面上所有的input元素//form[1]/input#查找页面上第一个form元素内的直接子input元素(即只包括form元素的下一级input元素,使用绝对路径表示,单/号)//form[1]//input#查找页面上第一个form元素内的所有子input元素(只要在form元素内的input都算,不管还嵌套了多少个其他标签,使用相对路径表示,双//号)//form[1]#查找页面上第一个form元素//form[@id='loginForm']#查找页面上id为loginForm的form元素//input[@name='username']#查找页面上具有name属性为username的input元素//form[@id='loginForm']/input[1]#查找页面上id为loginForm的form元素下的第一个input元素//input[@name='continue'][@type='button']#查找页面具有name属性为contiune并且type属性为button的input元素//form[@id='loginForm']/input[4]#查找页面上id为loginForm的form元素下第4个input元素
写法为:
element = driver.find_element(By.XPATH, '路径')
绝对路径
调试模式找到元素右键复制
不建议写绝对路径!!!
定位模糊匹配
contains关键字:
//a[contains(@href, ‘logout’)]
寻找页面中href属性值包含有logout这个单词的所有a元素
start-with关键字:
//a[starts-with(@name, ‘start)])
寻找name属性以start开头的a元素。其中@后面的name可以替换成元素的任意其他属性
text关键字:
//*[text()=’确定’]
一个简单粗暴的定位方式,无需知道属于什么标签元素,常用于纯文字查找,也可用于链接元素文本查找
//a[contains(text(), ’退出’)]
用于知道超链接上显示的部分或全部文本信息时
find_element和find_elements:
- find_element返回匹配到的第一个标签对象;find_elements返回列表
- find_element匹配不到抛出异常;find_elements匹配不到返回空列表
元素操作
示例1:
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By
import time
chrome_options = Options()
chrome_options.page_load_strategy ='eager'
service = Service('chromedriver.exe路径')
driver = webdriver.Chrome(service=service, options=chrome_options)
driver.get("https://www.baidu.com")
driver.find_element(By.ID,'kw').send_keys('python')
driver.find_element(By.ID,'su').click()
time.sleep(5)
driver.close()
示例2:
el_list:list= driver.find_elements(By.XPATH,"/html/body/div[6]/div[2]/ul/li/div[2]/h2/a")for el in el_list:print(el.text)print(el.get_attribute('href'))
标签页(窗口)切换
我们在使用浏览器的时候,会自动转到新的标签页,但selenium不会这样,我们需要进行操作来实现
利用窗口句柄切(指向标签页对象的标识)换到句柄指向的标签页
driver.get("url")
time.sleep(3)print(driver.current_url)#获取当前页面的urlprint(driver.window_handles)#获取当前所有存在的窗口句柄,多个句柄以列表方式存储
driver.find_element(By.XPATH,"/html/body/div[6]/div[2]/ul/li[1]/div[2]/h2").click()print(driver.current_url)print(driver.window_handles)
time.sleep(3)
driver.switch_to.window(driver.window_handles[-1])#切换至新窗口print(driver.current_url)
time.sleep(3)
driver.close()#关闭当前窗口
driver.switch_to.window(driver.window_handles[0])#切换至原窗口print(driver.current_url)
iframe切换
<iframesrc="1.html"id="hogwarts_id"name="hogwarts_name"></iframe>
实现:
# index:传入整型的参数,从 0 开始,这里的 0 就是第一个 frame
driver.switch_to.frame(0)#id:iframe 的 id
driver.switch_to.frame("hogwarts_id")#name: iframe 的 name
driver.switch_to.frame("hogwarts_name")#WebElement: 传入 `selenium.webelement` 对象
driver.switch_to.frame(driver.find_element(By.TAG_NAME,"iframe"))
在切换页面之后,如果还想操作原页面,则可以使用:
driver.switch_to.default_content()
嵌套多层iframe的切换:
<html><iframesrc="a.html"id="frame1"><iframesrc="b.html"id="frame2">
<input id="kw" / >
</iframe></iframe></html>
多层嵌套的情况下,如果要从主界面切换到第二层iframe,则需要一层一层的切换进去,即先切换到frame1,再切换到frame2,而不是直接切换进入frame2
driver.switch_to.frame("frame1")
driver.switch_to.frame("frame2")
selenium还提供了一个切换到父frame的方法,比如我们切换到frame2之后,要想切换到frame1操作,则不需要先切回主界面再切换到frame,而是使用如下方法:
driver.switch_to.parent_frame()
需要注意的是,如果当前已经是主页面,则使用此方法无效
cookies操作
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By
import time
chrome_options = Options()
chrome_options.page_load_strategy ='eager'
service = Service('chromedriver.exe路径')
driver = webdriver.Chrome(service=service, options=chrome_options)
driver.get("https://www.baidu.com")#print(driver.get_cookies())#转换为字典格式
cookies ={}for data in driver.get_cookies():
cookies[data['name']]= data['value']#字典推导式
cookies1={data['name']: data['value']for data in driver.get_cookies()}print(cookies)print(cookies1)
driver.delete_cookie('CookieName')#删除一条cookie
driver.delete_all_cookies()#删除所有cookie
页面等待
强制等待
time.sleep()
缺点:不智能:设置的时间短,元素还没有加载出来;设置的时间长,则会浪费时间
隐式等待
隐式等待针对的是元素定位(设置一次,所有元素定位都会按照设定),隐式等待设置了一个时间,在一段时间内判断元素是否定位成功,如果完成了,就进行下一步;如果在设置的时间内没有定位成功,则会报超时加载
#隐式等待from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By
import time
chrome_options = Options()
chrome_options.page_load_strategy ='eager'
service = Service('chromedriver.exe路径')
driver = webdriver.Chrome(service=service, options=chrome_options)
driver.implicitly_wait(5)#设置隐式等待时间为5秒
driver.get("https://www.baidu.com")
driver.find_element(By.ID,'kkww')#5秒钟内定位不到元素,报错
显式等待
明确等待某一个元素
每经过多少秒就查看一次等待条件是否达成,如果达成就停止等待,继续执行后续代码;如果没有达成就继续等待直到超过规定的时间后报超时异常
多用于软件测试,想要了解请自行查找
Chrome无界面模式
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.common.by import By
import time
chrome_options = Options()
chrome_options.page_load_strategy ='eager'
service = Service('chromedriver.exe路径')
chrome_options.add_argument("--headless")#添加开启无界面模式的命令
chrome_options.add_argument("--disable-gpu")#添加开启禁用gpu的命令
driver = webdriver.Chrome(service=service, options=chrome_options)
driver.get("https://www.baidu.com")
driver.save_screenshot('baidu.png')
配置代理:
chrome_options.add_argument("--proxy-server=http://113.254.44.242:8382")
注意:更换ip代理必须重启浏览器
配饰UserAgent:``chrome_options.add_argument(“–user-agent=XXXX”)`
案例
【Python爬虫】案例_斗鱼
版权归原作者 Root_Smile 所有, 如有侵权,请联系我们删除。