爬虫阶段性总结
Posted ZSYL
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了爬虫阶段性总结相关的知识,希望对你有一定的参考价值。
爬虫阶段性总结
requests模块
resonse.content.headers:响应头
resonse.headers:请求头
Set-Cookie:即是Cookie值
response.cookies:object:cookieJar
# 获取字典
dict_cookies = reequests.utils.dict_from_cookiejar(response.cookies)
# 字典转对象
jar_cookie = request.utils.cookie_jar_from_dict(dict_cookies)
response.json():json数据
response.content.decode():推荐使用,不用考虑编码,直接二进制解码,自动根据编码类型解码
使用cookie参数保持会话
- 构建cookie参数
- 再请求时将cookie字典赋值给cookie参数
- request.get(url, cookie)
超时参数timeout的使用
request.get(url, timeout=3) # 3s
代理的使用
- 代理是一个ip,指向的是一个代理服务器,作用是转发请求
verify参数和CA认证
SSLerror:certificate verify failed
证书认证失败
request.get(url, verify=False) # 忽略证书
post
命令行获取输入内容
import sys
print(sys.argv) # 返回的是当前.py文件的绝对路径
# 之后进入命令行,python3 .py China
# 返回 [.py, CHina]
# 因此可以从命令行获取所需内容
word = sys.argv[1]
king = King(word)
king.run()
数据来源:
- 固定值 抓包比较不变值
- 输入值 抓包比较根据自身变化值
- 预设值-静态文件 需要提前从静态html中获取
- 预设值-发送请求 需要对指定地址发送请求
- 在客户端生成的 分析js,模拟生成数据
session
作用:自动处理cookie
场景:连续的多次请求
数据提取
响应分类
结构化
- json数据
- json模块
- re模块
- jsonpath模块
- xml数据(低频出现)
- re模块
- lxml模块
非结构化
- html
- re模块
- lxml模块
jsonpath
多层嵌套的复杂字典直接提取数据
语法:
- $:根结点
- .:子节点
- …:子孙节点
jsonpath(data, '$.key1.key2.key3') # 结果为列表
jsonpath(data, '$..key3')
xpath
节点选择语法
html/head/title # 绝对路径
html//title
//title # 相对路径
//title/text() # 从开闭标签之间获取文本内容
//link/@href # 从选中的节点标签中获取指定属性的值
/html/body/div[3]/div[1]/div[last()-1] # 选择倒数第二个
/html/body/div[3]/div[1]/div[position() > 10] # 范围选择
//div[@id='content-left']/div/@id # 相对路径,最后的/@是取属性值,[@]:通过标签属性名和属性值修饰节点
//div[span[2] > 9.4] # div下属性span[2]的值大于9.4:电影评分大于9.4
//span[i>2000] # 节点的属性值筛选,标签i的值>2000,通过子节点的值修饰节点
//div[contains(@id, 'qiushi_tag')] # 包含修饰
//span(contains(text(), '下一页'))
//*[@id='content-left'] # 通配,选择被[id]修饰的节点
//*/@* # 选取所有的属性值
//node() # 选取所有的节点
//td/a/@href # 获取a标签中的链接
//h2/a|//td/a # xpath复合使用
/:隔开的是节点
@:选择属性
注意:
找下一页的时候,不要使用索引
etree.HTML(html_str) 可以自动补全标签
js解析
- 定位js文件(找出生成出加密数据的js文件)
- 通过initiator搜索关键字定位到js文件
- 通过search搜索关键字定位js文件
- 通过元素绑定的事件监听函数找到js文件
- 分析js代码,掌握加密步骤
- 模拟加密步骤,使用Python代码的方法重现
- 使用第三方模块加载js:js2py、pyv8、executejs,splash
- 纯Python代码实现
- 定位 分析 重现
min
x
f
(
x
)
=
x
2
+
4
x
−
1
(
1
)
s
.
t
.
x
+
1
≤
0
(
2
)
s
.
t
.
−
x
−
1
≤
0
\\min _{x} f(x)=x^{2}+4 x-1 \\\\ (1)s.t. x+1 \\leq 0 \\\\(2) s. t. -x-1 \\leq 0
xminf(x)=x2+4x−1(1)s.t.x+1≤0(2)s.t.−x−1≤0
地址去重
- url
- url-hash
- 布隆过滤器
文本内容去重
- 编辑距离
- simhash
Scrapy
完成爬虫流程
- 修改起始的url
- 检查修改允许的域名
- 在parse方法中实现爬取逻辑
保存数据
在``pipelines.py`文件定义对应数据的操作
定义一个管道类
重写管道类的process_item方法
precess_item方法处理完item之后需返回engine
在setting文件中启动管道
scrapy list 显示已存在的爬虫列表
rm *.json 删除.json结尾的文件
crwalspider
继承自 Spider 爬虫类
自动根据规则提取链接并且发送给引擎
- 创建crawlspider爬虫
- scrapy genspider [-t crawl] name domains # -t 选择模板
中间件的使用方法
- 在middlerware.py中定义中间件类
- 在中间件类中重写请求或者响应的方法
process_request
- None:如果所有的下载器中间件都返回None,则请求最终被交给下载器
- request:如果返回为请求,则将请求交给调度器
- response:将响应对象交给spider进行解析
process_response
- 在setting中间中开启中间件的使用
分布式爬虫
加快项目的运行速度,但是需要的资源(硬件&网络)依然还是原有的
单个节点的不稳定性不能影响整个系统的稳定性
分布式特点:
协作
加快整个任务的执行速度
稳定性更高,单个节点不会影响整个任务
self.key = "dmoz:items" % {'spider': 'dmoz'}
分布式爬虫的实现步骤
- 实现一个普通爬虫
2. 修改为分布式爬虫
1.修改爬虫文件
1.导入分布式爬虫类
2.修改爬虫类的继承
3.注销起始的url和允许的域
4.redis_key从数据库中获取起始的url
5.__init__动态的获取允许的域
2.修改配置文件
1.copy配置文件然后根据当前项目进行修改
2.手写5个配置项
3.运行
运行爬虫节点
scrapy runspider 爬虫文件
启动爬虫
lpush redis_key start-url
ifconfig:获取IP信息
ps aux |grep redis:开启Redis数据库
'%{spider}s:items' % {'spider': demoz} # 占位符
分布式爬虫编写流程
-
编写普通爬虫
- 创建项目
- 明确目标
- 创建爬虫
- 保存内容
-
改造分布式爬虫
-
改造爬虫
- 导入scrapy_redis中的分布式爬虫类
- 继承类
- 注销 start_urls & allowed_domains
- 设置 redis_key 获取 start_urls
- 设置__init___获取允许的域
-
改造配置文件
copy配置参数
-
分布式爬虫总结
使用场景
- 数据量特别大
- 数据要求时间比较紧张
分布式的实现
-
scrapy_redis 实现分布式
-
普通爬虫实现分布式:实现去重集合与任务队列的共享
分布式的步数
- poor – 若干台普通笔记本电脑
- 小康 – 一台服务器虚拟若干台电脑
- 土豪 – 数据采集服务台(15)管理(3-4)存储(10)
爬虫的抓包
手刃JD
关键的JS代码:
, H = (r("pFHu"),
Object(u.b)()((function(e) {
var t = e.sonList;
return c.a.createElement(c.a.Fragment, null, c.a.createElement("dt", null, c.a.createElement("a", {
href: "//channel.jd.com/".concat(t.fatherCategoryId, "-").concat(t.categoryId, ".html")
}, t.categoryName), c.a.createElement("b", null)), c.a.createElement("dd", null, t && t.sonList.map((function(e, r) {
return c.a.createElement("em", {
key: r
}, c.a.createElement("a", {
href: "//list.jd.com/".concat(t.fatherCategoryId, "-").concat(e.fatherCategoryId, "-").concat(e.categoryId, ".html")
}, e.categoryName))
}
))))
}
)))
scrapy genspider book jd.com # 创建爬虫,后编写爬虫
Scrapy_splash
scrapy的一个组件
功能:
- scrapy-splash能够模拟浏览器加载js,并返回加载后的完整代码
使用:
- 安装
- splash
-
- 安装docker
- 下载splash镜像
-
- python模块
- splash
以上是关于爬虫阶段性总结的主要内容,如果未能解决你的问题,请参考以下文章
requests库与 lxml 库常用操作整理+总结,爬虫120例阶段整理篇