大家好,又见面了,我是你们的朋友全栈君。
时间:2020年6月3日10:28:48 作者:钟健 概要:关于scrapy爬虫应对网页JavaScript动态渲染问题 关键字:scrapy crapy-splash
scrapy爬虫与传统爬虫一样,都是通过访问服务器端的网页,获取网页内容,最终都是通过对于网页内容的分析来获取数据,这样的弊端就在于他更适用于静态网页的爬取,而面对js渲染的动态网页就有点力不从心了,因为通过js渲染出来的动态网页的内容与网页文件内容是不一样的。
腾讯招聘:https://careers.tencent.com/search.html
这个网站第一眼看过去是非常中规中矩的,结构也很鲜明,感觉是很好爬的样子,但是当你查看他的网页文件的时候,就会发现:
网页文件并没有太多的内容,全部是引用了js做的动态渲染,所有数据都在js中间,这就使我们无法对于网页的结构进行分析来进行爬取数据
那我们如何,获取到它实际显示的页面,然后对页面内容进行分析呢?
目前scrapy解决动态网页渲染问题的主要有以下三种的解决方法:
就是传统的结合浏览器进行渲染,优点就在于,浏览器能访问什么,他就能够获取到什么,缺点也很明显,因为它需要配合浏览器,所以它的速度很慢。
由于ScrapySplash要在docker里使用,我们先安装docker,过程比较复杂痛苦,略。
在安装的过程中有一个非常严峻的问题,那就是docker,需要开启win10 hyper虚拟服务,这与你在电脑上安装的VM是相冲突的,所以在使用docker,的时候无法使用VM虚拟机,而且每次切换时都需要重启电脑,目前这个问题暂时无法解决。
docker run -p 8050:8050 scrapinghub/splash
这个过程异常异常的慢,而且必须是国内的镜像,才能够下载下来。
所以我配置了两个国内的下载IP,一个网易的,一个阿里云的。
{
"registry-mirrors": [
"https://registry.docker-cn.com",
"http://hub-mirror.c.163.com",
"https://docker.mirrors.ustc.edu.cn"
],
"insecure-registries": [],
"debug": true,
"experimental": false
}
下载完成过后,打开浏览器访问:http://localhost:8050/
这就表示已经安装完成了,命令行不能关闭哦
pip install scrapy-splash
python没有花里胡哨的安装过程。
1.项目的创建和配置过程略
2.settings.py的配置
PIDER_MIDDLEWARES = {
'scrapy_splash.SplashDeduplicateArgsMiddleware': 100,
}
DOWNLOADER_MIDDLEWARES = {
'scrapy_splash.SplashCookiesMiddleware': 723,
'scrapy_splash.SplashMiddleware': 725,
'scrapy.downloadermiddlewares.httpcompression.HttpCompressionMiddleware': 810, # 不配置查不到信息
}
HTTPCACHE_ENABLED = True
HTTPCACHE_EXPIRATION_SECS = 0
HTTPCACHE_DIR = 'httpcache'
SPLASH_URL = "http://localhost:8050/" # 自己安装的docker里的splash位置
# DUPEFILTER_CLASS = "scrapy_splash.SplashAwareDupeFilter"
HTTPCACHE_STORAGE = 'scrapy_splash.SplashAwareFSCacheStorage'
3.爬虫的设计
def start_requests(self):
splah_args = {
"lua_source": """ function main(splash, args) assert(splash:go(args.url)) assert(splash:wait(0.5)) return { html = splash:html(), png = splash:png(), har = splash:har(), } end """
}
headers = {
'User-Agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) '
'Chrome/72.0.3626.109 Safari/537.36',
}
yield SplashRequest(url=self.start_url, callback=self.parse, args=splah_args,
headers=headers)
SplashRequest
,我们不再使用Request
,而是使用scrapy-splash的请求方式,这里也体现了它与scope框架的完美融合。
4.解析打印数据
def parse(self, response):
print(response.text)
job_boxs = response.xpath('.//div[@class="recruit-list"]')
for job_box in job_boxs:
title = job_box.xpath('.//a/h4/text()').get()
print(title)
这是通过渲染以后的网页数据
这里我们直接获取职位的标题
这就表明scrapy爬虫应对动态网页渲染问题已经解决,也就意味着scrapy能够处理大部分的网页,并可以应对一些图形验证问题
这时候我们就要做取舍了,我们想要的是所有数据,并不是渲染出来的网页,与解析网页内容相比,直接通过它的接口获取json数据,更加快捷方便,速度更快,所以我们就要做出取舍,在这里直接获取接口数据将更好,错误率会更低,速度也会更快。
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/159469.html原文链接:https://javaforall.cn