-
scrapy下载图片
- 爬虫类中,将img_src作为item的属性yield即可
- 关键实现点在管道类里
- 导入一个图片的管道类 from scrapy.pipelines.images import ImagesPipeline
- 发请求 import scrapy
- 重写图片管道类的三个父类方法
- get_media_requests : 对媒体资源进行请求(下载)
- file_path : 指明数据存储的路径
- item_completed : 将item传递给下一个即将执行的管道类
-
CrawlSpider
- 一种基于scrapy进行全站数据爬取的一种新的技术手段
- Spider的一个子类
- 链接提取器:LinkExtractor
- 实例化了一个链接提取器对象
- 根据指定规则(allow='正则表达式')进行指定链接的提取
- link = LinkExtractor(allow=r'id=1&page=d+')
- 规则解析器:Rule
- rules = (Rule(link, callback='parse_item', follow=True),)
- 将link作用到了Rule构造方法的参数中
- 将链接提取器取到的链接进行请求发送且根据指定规则对请求到的数据进行数据解析
- follow=True 将链接提取器继续作用到提取的链接所对应的页面中
- 链接提取器:LinkExtractor
- 使用流程:
- 新建一个工程
- cd 工程
- 新建一个爬虫文件: scrapy genspider -t crawl spiderName www.xxx.com
- 深度爬取
- 一个link对应一个Rule,解析不同的内容指定不同的回调函数
- 不使用手动请求和请求传参
- 不同的内容指定不同的item类,不同的回调函数yield给管道类
- 管道类先判断是哪个item,分别取值
- item.class.name 用item的类名判断
- 存储到表的时候,找两个item的相同点(如编号)
- 先插入title和num,然后条件插入content(while num==num)
-
分布式
- 概念:需要搭建一个分布式的机群,然后在机群的每一台电脑中执行统一程序,让其对某一个网站的数据进行联合分布爬取
- 原生的scrapy框架是不可以实现分布式的
- 因为调度器不共享!
- 管道不共享,爬取的数据难以汇总!
- 如何实现?
- scrapy+scrapy_redis 实现分布式
- scrapy_redis组件的作用?
- 可以提供可被共享的调度器和管道
- 特性:数据只可以存储到redis数据库
- 分布式的实现流程:
-
1.pip install scrapy_redis
-
2.创建工程
-
3.cd 工程目录
-
4.创建爬虫文件(a.创建基于Spider类的 b.创建基于CrawlSpider类的)
-
5.修改爬虫类:
- 导包:from scrapy_redis.spiders import RedisCrawlSpider
- 修改当前爬虫类的父类为RedisCrawlSpider
- allowed_domains和start_urls删除
- 添加一个新属性:redis_key = 'fbsQueue',表示的是可以被共享的调度器队列的名称
- 编写爬虫类的常规操作
-
6.settings配置文件的配置:
-
UA伪装
-
Robots
-
管道的指定:
ITEM_PIPELINES = {
'scrapy_redis.pipelines.RedisPipeline': 400
} -
指定调度器:
- 增加一个去重容器类的配置,使用redis的set集合来存储请求的指纹数据,实现请求去重的持久化
DUPEFILTER_CLASS = "scrapy_redis.dupefilter.RFPDupeFilter" - 使用scrapy_redis组件自己的调度器
SCHEDULER = "scrapy_redis.scheduler.Scheduler" - 配置调度器是否要持久化,增量式
SCHEDULER_PERSIST = True
- 增加一个去重容器类的配置,使用redis的set集合来存储请求的指纹数据,实现请求去重的持久化
-
指定redis数据库
REDIS_HOST = 'redis服务的ip'
REDIS_PORT = 6379 -
redis的配置文件进行配置(redis.windows.conf):
- 关闭默认绑定:line56 #bind 127.0.0.1
- 关闭保护模式:line75 #protected-mode no
-
-
7.启动redis的服务端和客户端:
- cd 到redis程序所在文件
- redis-server.exe redis.windows.conf
- 另起一个cmd redis-cli
-
8.启动程序:
- cd 到spiders文件夹
- scrapy runspider xxx.py
-
9.向调度器的队列扔入一个起始url:
- 队列是存在redis中的
- 打开redis客户端
- lpush fbsQueue http://.....
-
-
增量式
-
概念:用于监测网站数据更新的情况
-
应用:
- 深度爬取 http://www.4567kan.com/frim/index1.html
- 所有页码的 电影名称 以及 详情页的电影简介
- 非深度爬取 https://www.qiushibaike.com/text/
- 所有页码的 当前页面的段子(段子会更新)
- 深度爬取 http://www.4567kan.com/frim/index1.html
-
核心机制:去重 redis的set实现
-
深度爬取
- 对详情页的url去重:利用redis插入数据返回1或0
- 必须要有两张表,一张存储详情页url,一张存储爬取的数据
-
非深度爬取
- 也要有两张表
- 将爬取到的数据做成两份,一份原文(作为明文存到数据表),一份数据指纹(作为记录存到记录表)
- 之后每次往数据表插入新数据之前,都要将该数据转为数据指纹到记录表查看是否存在
-
-
图片懒加载
- 没有出现在可视范围内的图片不加载src属性
- 应用到标签的伪属性
-
总结反爬机制:
- robots
- UA伪装
- 动态数据的捕获
- 验证码
- 代理
- cookie
- 动态变化的请求参数
- js加密
- js混淆
- 图片懒加载
- selenium:规避检测