python selenium 查找隐藏元素 自动播放视频功能
作者:zdz 发布时间:2022-03-01 18:54:14
在使用python做爬虫的过程中,有些页面的的部分数据是通过js异步加载的,js调用接口的请求中有时还带有些加密的参数很难破解无法使用requests这样的包直接爬取数据,因此需要借助seleniu来完成js的自动加载。
通过selenium 模拟浏览器的真是操作来获取页面中的所有请求,并且可以查找到一下页面上一些隐藏的元素,这些元素在html源码中无法看到,并且和能通过xpath和正则来捕获,因此需要使用selenium来查找隐藏元素,例如视频网站的播放按钮
代码如下
import time
# 导入自动化测试模块
from selenium import webdriver
from selenium.webdriver.common.desired_capabilities import DesiredCapabilities
from selenium.webdriver.common.action_chains import ActionChains
import re
import json
d = DesiredCapabilities.CHROME
d['loggingPrefs'] = {'performance': 'ALL'}
# 设置谷歌浏览器参数,设置语言和浏览器版本(使用真实浏览器头信息代替字符浏览器头)
options = webdriver.ChromeOptions()
options.add_argument('lang=zh_CN.UTF-8')
options.add_argument('user-agent="Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/73.0.3683.86 Mobile Safari/537.36"')
# 建立一个浏览器对象,调用PhantoJS来生成一个对象
browser = webdriver.Chrome(executable_path='D:\Python36\chromedriver.exe', chrome_options=options, desired_capabilities=d)
video_url = 'https://v.youku.com/v_show/id_XNDIyMjU1NjgzMg==.html?spm=a2ha1.12675304.m_2556_c_8261.d_2&s=a4de6bdc5675415ea280&scm=20140719.manual.2556.show_a4de6bdc5675415ea280'
browser.get(video_url)
time.sleep(10)
menu = browser.find_element_by_css_selector(".ykplayer") # 查找页面隐藏元素
# menu = browser.find_element_by_css_selector("div.x-video-play-ico.i-pause > dt").text
print(menu)
print(type(menu))
menu = browser.find_element_by_css_selector(".ykplayer").text # 获得隐藏元素的内容
print(menu)
print(type(menu))
###################
#ActionChains(browser).click()
browser.find_element_by_css_selector('.ykplayer').click() # 查找到隐藏元素位置后执行点击鼠标左键操作
time.sleep(10)
lo = browser.get_log('performance') # 捕获浏览器network中的数据
browser.get_network_conditions()
datalist = []
for entry in lo:
try:
print(entry)
datalist.append(entry)
except Exception as e:
continue
browser.close()
视频中被播放按钮是一个隐藏元素,用xpaht定位到指定的标签后也无法获取这个标签中的元素
通过 browser.find_element_by_css_selector(“.ykplayer”)
方法查找 .ykplayer 可以查找到,查找后输出的内容这个视频的标题,这样就实现了使用chromedriver
自动播放视频的功能
这里虽然实现的视频自动播放,但是请求优酷视频的视频地址的接口调用的结果却依然没法通过 browser.get_log(‘performance')
来获得,原因是有一部分数据没有全部加载,但接口实际已经取得了完整的数据。虽然可以通过 get_log中的结果获得请求的地址,但是这个请求的地址在此使用requests进行请求会提示无权访问,可以看到这个请求已经有请求体了,但是使用get_log却无法捕获。
而且这个请求地址是一次性的,在次请求的结果是没权限
{"cost":0.003000000026077032,"data":{"error":{"note":"客户端无权播放,201","code":-6004}},"e":{"code":0,"provider":"hsfprovider","desc":""}}
要解决这个问题需要使用到browsermob-proxy
利用BrowserMob Proxy实现类似chrome的开发者工具中network的功能,
监控浏览器中该页面的request,获取对应的response,从而得到对应的json数据。
其大致原理是设置一个本地代理,并监控浏览器通过该代理的网络活动。
最后,我的解决方案是:python3 + selenium + chrome + browsermob-proxy
下载好BrowserMob Proxy和chromedriver,并记住对应的路径,稍后需要配置。
https://bmp.lightbody.net/
http://npm.taobao.org/mirrors/chromedriver/
另外,使用browsermob-proxy
需要安装Java依赖环境,首次安装后可能需要重启。
python的环境可安装anaconda获得,然后是安装额外的python库
pip install browsermob-proxy
pip install selenium
软件环境配置完成后,可开始搭建抓取 * 页的框架,
下面是我做的一个简单框架(browsermonitor.py),其中未涉及数据的加工,可针对需要抓取的网页,直接继承后,根据需求加工数据:
?
"""step 1 导入依赖库"""
from os import path
from browsermobproxy import Server
from selenium import webdriver
import re
"""step 2 新建浏览器监控类"""
class Monitor(object):
"""
step 3 配置chromedriver 和 browermobproxy 路径
需要使用完整路径,否则browsermobproxy无法启动服务
我是将这两个部分放到了和monitor.py同一目录
同时设置chrome为屏蔽图片,若需要抓取图片可自行修改
"""
PROXY_PATH = path.abspath("./browsermob-proxy/bin/browsermob-proxy.bat")
CHROME_PATH = path.abspath("./chromedriver.exe")
CHROME_OPTIONS = {"profile.managed_default_content_settings.images":2}
def __init__(self):
"""
类初始化函数暂不做操作
"""
pass
def initProxy(self):
"""
step 4 初始化 browermobproxy
设置需要屏蔽的网络连接,此处屏蔽了css,和图片(有时chrome的设置会失效),可加快网页加载速度
新建proxy代理地址
"""
self.server = Server(self.PROXY_PATH)
self.server.start()
self.proxy = self.server.create_proxy()
self.proxy.blacklist(["http://.*/.*.css.*","http://.*/.*.jpg.*","http://.*/.*.png.*","http://.*/.*.gif.*"],200)
def initChrome(self):
"""
step 5 初始化selenium, chrome设置
将chrome的代理设置为browermobproxy新建的代理地址
"""
chromeSettings = webdriver.ChromeOptions()
chromeSettings.add_argument('--proxy-server={host}:{port}'.format(host = "localhost", port = self.proxy.port))
chromeSettings.add_experimental_option("prefs", self.CHROME_OPTIONS)
self.driver = webdriver.Chrome(executable_path = self.CHROME_PATH, chrome_options = chromeSettings)
def genNewRecord(self, name = "monitor", options={'captureContent':True}):
"""
step 6 新建监控记录,设置内容监控为True
"""
self.proxy.new_har(name,options = options)
def getContentText(self, targetUrl):
"""
step 7 简单的获取目标数据的函数
其中 targetUrl 为浏览器获取对应数据调用的url,需要用正则表达式表示
"""
if self.proxy.har['log']['entries']:
for loop_record in self.proxy.har['log']['entries']:
try:
if re.fullmatch(targetUrl , loop_record["request"]['url']):
return loop_record["response"]['content']["text"]
except Exception as err:
print(err)
continue
return None
def Start(self):
"""step 8 配置monitor的启动顺序"""
try:
self.initProxy()
self.initChrome()
except Exception as err:
print(err)
def Quit(self):
"""
step 9 配置monitor的退出顺序
代理sever的退出可能失败,目前是手动关闭,若谁能提供解决方法,将不胜感激
"""
self.driver.close()
self.driver.quit()
try:
self.proxy.close()
self.server.process.terminate()
self.server.process.wait()
self.server.process.kill()
except OSError:
pass
if __name__ == '__main__':
monitor = Monitor()
monitor.Start()
monitor.genNewRecord()
# 这使用优酷视频的地址
url = 'https://v.youku.com/v_show/id_XNDIyMjU1NjgzMg==.html?spm=a2ha1.12675304.m_2556_c_8261.d_2&s=a4de6bdc5675415ea280&scm=20140719.manual.2556.show_a4de6bdc5675415ea280'
monitor.driver.get(url)
targetUrl = "https://ups.youku.com/ups/get.json.*" # 这是获取视频播放地址的接口请求的前缀
text = monitor.getContentText(targetUrl)
monitor.Quit()
总结
以上所述是小编给大家介绍的python selenium 查找隐藏元素 自动播放视频功能,网站的支持!
如果你觉得本文对你有帮助,欢迎转载,烦请注明出处,谢谢!
来源:http://www.zhengdazhi.com/archives/1765


猜你喜欢
- 内容摘要:本文详细介绍了SQL Server导入导出数据的方法:(1)导出导入SQL Server里某个数据库,(2)导
- 1、背景介绍在采用通常的socket抓包方式下,操作系统会自动将收到包的VLAN信息剥离,导致上层应用收到的包不会含有VLAN标签信息。而l
- 最近一个项目开发要用到PHP技术导出Word文档,比较了几种方案,首先是使用Microsoft Office自带的ActiveX/COM组件
- 简单邮件传输协议(SMTP)是一种协议,用于在邮件服务器之间发送电子邮件和路由电子邮件。Python提供smtplib模块,该模块定义了一个
- 测试异常情况-- 1. 查询张三余额select * from account where name = '张三';-- 2
- 这只是个asp小技巧类的东西,它虽然适合在每个不同文件名里调用这个函数,但是也是有前提的,下面让我们来仔细看看其中的原委。 &n
- 线程间通信方法 1. 通信方法线程间使用全局变量进行通信 2. 共享
- 在我们使用查询语句的时候,经常要返回前几条或者中间某几行数据,这个时候怎么办呢?不用担心, mysql已经为我们提供了这样一个功
- 目录前置知识有哪些可变对象,哪些不可变对象?不可变对象和可变对象的区别?不可变对象的应用场景从内存角度出发说下有什么区别?不可变对象可变对象
- 本文实例讲述了php mysql procedure实现获取多个结果集的方法。分享给大家供大家参考,具体如下:protected funct
- Python 解释器内置了一些常量和函数,叫做内置常量(Built-in Constants)和内置函数(Built-in Function
- Python list内置sort()方法用来排序,也可以用python内置的全局sorted()方法来对可迭代的序列排序生成新的序列。1)
- 从大规模数据集中寻找物品间的隐含关系被称作关联分析或关联规则学习。过程分为两步:1.提取频繁项集。2.从频繁项集中抽取出关联规则。 频繁项集
- 一、在搭建的时候参考以下文章http://www.cnblogs.com/zsy/archive/2016/02/28/5223957.ht
- 下载代码Cookie池(这里主要是微博登录,也可以自己配置置其他的站点网址)下载代码GitHub:https://github.com/Py
- 在本章中,您将详细了解Python中各种加密模块.加密模块它包含所有配方和基元,并在Python中提供高级编码接口.您可以使用以下命令安装加
- 目录前言算法原理目标函数算法流程 Python实现总结前言K-Means 是一种非常简单的聚类算法(聚类算法都属于无监督学习)。给
- 新建项目时,选择新建虚拟环境项目打开后,启动终端,却经常发现,并没有开启虚拟环境,导致一些包都被安装到全局环境中。一种解决办法是手动开启虚拟
- 很多时候,我发现自己需要进行生成报告、输出文件或字符串的任务。它们或多或少都会遵循某种模式,通常这些模式是如此相似,以至于我们希望拥有一个可
- 当用到socket来进行网络程序开发时,大多数情况下会遇到中文字符的发送与接收,这时若对发送的字符串用默认的方式进行处理,则一般会得到一堆乱