爬虫工作量由小到大的思维转变---<第五十章 Scrapy 深入理解Scrapy爬虫引擎(1)--核心功能>

本文主要是介绍爬虫工作量由小到大的思维转变---<第五十章 Scrapy 深入理解Scrapy爬虫引擎(1)--核心功能>,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

前言:

        Scrapy的引擎是该框架的中心角色,负责协调整个爬虫流程的执行。引擎充当了整个框架的核心,并提供了一套强大灵活的机制来管理请求的调度、页面的下载、数据的提取和处理等关键任务。以下是关于Scrapy引擎的详细论述。

  1.         首先,Scrapy引擎负责调度和管理请求。它从待处理的请求队列中获取请求,并根据其优先级和调度策略来决定下一个要处理的请求。引擎允许用户根据需要自定义调度策略,比如根据网站的限制或页面的特定标记进行请求的处理顺序调整。
  2.         其次,引擎负责请求的发送和页面的下载。它将请求交给下载器,并接收下载器返回的响应。引擎也负责处理下载过程中可能发生的错误或异常情况,并采取相应的动作,如重新发送请求或中止爬取。
  3.         此外,引擎还负责将页面的响应传递给爬虫中指定的解析函数。解析函数根据页面的结构和规则,提取所需的数据,并将数据传递给管道进行进一步的处理。引擎协调解析函数的调用和数据的传递过程,确保数据能够正确流经各个组件。
  4.         引擎还支持扩展和中间件机制,使得开发者能够根据自己的需求来定制请求和响应的处理流程。不同类型的中间件可以用于预处理请求、处理响应、进行身份验证等,以增强爬虫的灵活性与功能。
  5.         最后,引擎提供了事件和信号机制,允许用户自定义触发和处理特定事件的逻辑。这些事件可以在不同的爬虫流程阶段中触发,如开始爬取、发送请求、处理响应等。通过这样的机制,用户可以监控和控制爬虫的行为,并根据需要进行相关操作。

综上所述,Scrapy引擎作为中心角色,承担了整个爬虫框架的协调和管理任务。它通过请求调度、页面下载、数据提取和处理等功能,实现了高效、可定制的爬虫流程。引擎的灵活性和可扩展性使得开发者能够构建强大的网络爬虫应用,满足各种需求。

正文:

Scrapy引擎的核心功能

        首先,让我们考虑一个比喻:将Scrapy引擎看作是一个交通指挥中心。就像交通指挥中心负责协调车辆的行驶和交通流量一样,Scrapy引擎负责协调请求和响应的流动,确保整个爬取过程的顺利进行。

        在这个比喻中,我们可以把Spiders(爬虫)看作是道路系统的起点。Spiders定义了要爬取的网址、如何提取数据以及如何跟进新链接。Spiders就像是从交通指挥中心出发的车辆,它们提供了爬取的初始点。

        当Spiders生成请求时,它们将这些请求交给引擎。这就像是车辆通过交通指挥中心发送请求来获得进一步指示和行驶许可。Scrapy引擎接收到请求后,会将它们添加到调度器中,等待进一步处理。

        调度器可以被视为交通指挥中心的交通调度系统它负责管理所有的请求,决定下一个要处理的请求是什么。调度器根据请求的优先级和调度策略,决定将哪个请求发送给下载器进行处理。可以将调度器看作是交通指挥中心的交通灯和交通规则,确保请求的有序和合理流动。

        一旦请求被调度器发送给下载器,引擎就像是将请求交给车辆的司机一样,将请求转交给下载器。下载器负责下载请求对应的页面,并将下载完成的响应返回给引擎。这就好像是司机按照指示行驶到目的地并返回交通指挥中心的情景。

        在Scrapy中,下载器中使用了下载中间件机制,这可以类比为司机行驶途中遇到的检查站和道路设施。下载中间件可以用于在请求发送或响应返回过程中执行额外的处理。比如,可以在下载中间件中进行身份验证、设置代理或进行URL过滤等操作,以增强请求和响应的处理能力

        当引擎接收到下载器返回的响应后,会将响应交给Spiders进行处理。涉及到的响应处理函数也被称为解析函数。解析函数的作用是从响应中提取出需要的数据或者进一步生成新的请求。这就相当于车辆到达目的地后需要进行装卸和新的行驶指示。

        Spiders将从响应中提取的数据保存在Item中,并将Item交给Pipeline(管道)进行进一步的处理。比如,可以在管道中对数据进行清洗、验证和持久化操作。可以将Pipeline视为车辆抵达目的地后所进行的仓储和分配工作

总结起来,

  • Scrapy引擎的核心功能是协调整个爬取流程,确保各组件能够顺利工作。它负责处理请求和响应的流动,类似于交通指挥中心的角色。
  • 引擎接收请求并将其交给调度器,调度器决定请求的处理顺序并将其发送给下载器。
  • 下载器将下载完成的响应返回给引擎,引擎再将响应交给Spiders进行解析和数据提取。
  • Spiders将提取的数据保存在Item中,并交给Pipeline进行后续处理。

通过这样的流程,Scrapy引擎实现了整个爬虫框架的高效运转。

此外,Scrapy引擎还支持并发处理多个请求和响应。就像交通指挥中心需要同时处理多辆车辆的行驶一样,引擎可以调度并发处理多个请求,并在下载器和Spiders之间进行有效的调度和协调。这样可以提高爬取的效率和速度。

 借助事件和信号机制

Scrapy引擎还提供了灵活的扩展性。开发者可以根据需要,自定义和注册事件和信号,并编写相应的处理函数。这就好比交通指挥中心可以根据特定事件和信号触发相应的操作和指引,以适应不同的情况和需求。

总而言之,Scrapy引擎作为Scrapy框架的核心,承担着整个爬虫流程的调度和协调任务。它类似于交通指挥中心,负责管理请求和响应的流动,确保各组件能够有序地工作。通过调度、请求处理、数据提取和处理等功能,引擎实现了高效、可定制的爬虫流程。借助比喻,我们可以更好地理解Scrapy引擎的工作原理和核心功能。

引擎和调度器的交互:

Scrapy引擎和调度器之间的交互是实现整个爬虫流程的关键步骤。引擎负责将请求交给调度器,并获取调度器返回的下一个要处理的请求。这个交互过程可以通过以下步骤来解释:

  1. 引擎将初始请求传递给调度器:当Spiders生成初始请求时,它们将这些请求交给引擎。引擎接收到这些请求后,将它们添加到调度器中。

  2. 调度器接收和管理请求:调度器负责管理所有的请求,根据其优先级和调度策略决定下一个要处理的请求是什么。它维护一个请求队列,并提供了一套灵活的机制来管理请求的调度。

  3. 引擎获取下一个要处理的请求:引擎从调度器中获取下一个要处理的请求。这个请求可以是通过调度策略决定的优先级最高的请求。

  4. 引擎将请求发送给下载器:引擎将获取到的请求发送给下载器,下载器负责下载请求对应的页面。这一步骤实际上是引擎将请求转交给下载器执行相应的下载任务。

  5. 下载器将响应返回给引擎:下载器在完成页面下载后,将下载完成的响应返回给引擎。响应包含了页面的数据和一些附加信息。

  6. 引擎处理返回的响应:引擎接收下载器返回的响应后,可能会触发一系列的事件和信号。这些事件和信号可以被注册的处理函数捕获和处理。引擎还负责将响应传递给相应的解析函数进行数据提取和处理。

  7. 解析函数生成新的请求:解析函数从响应中提取出数据,并可能生成新的请求。引擎将这些新的请求交给调度器进行处理。

  8. 调度器重新处理新的请求:调度器接收到引擎发送的新的请求后,会重新根据调度策略和优先级进行处理。这个过程循环进行,直到没有新的请求要处理。

案例解释:
import scrapyclass MySpider(scrapy.Spider):name = "myspider"def start_requests(self):# 生成初始请求并通过引擎传递给调度器yield scrapy.Request(url="http://example.com", callback=self.parse)def parse(self, response):# 处理响应数据# 生成新的请求并通过引擎再次传递给调度器yield scrapy.Request(url="http://example.com/next", callback=self.parse_next)# 创建一个CrawlerProcess对象并启动爬虫
from scrapy.crawler import CrawlerProcessprocess = CrawlerProcess()
process.crawl(MySpider)
process.start()

引擎和下载器的交互:

引擎和下载器之间的交互是爬取过程中的另一个重要环节。引擎负责将请求发送给下载器,下载器负责下载页面并返回响应。以下是引擎和下载器的交互步骤:

  1. 引擎将请求发送给下载器:引擎从调度器获取待处理的请求后,将其发送给下载器执行页面下载任务。

  2. 下载器下载页面并返回响应:下载器接收到引擎发送的请求后,执行下载任务,从网络上获取对应页面的数据。下载器将下载完成的响应返回给引擎。

  3. 引擎处理返回的响应:引擎接收到下载器返回的响应后,可能会触发一系列的事件和信号。这些事件和信号可以被注册的处理函数捕获和处理。引擎还负责将响应传递给相应的解析函数进行数据提取和处理。

  4. 解析函数生成新的请求:解析函数从响应中提取出数据,并可能生成新的请求。引擎将这些新的请求再次发送给下载器进行处理,形成一个循环。

案例解释:
import scrapyclass MySpider(scrapy.Spider):name = "myspider"def start_requests(self):# 生成初始请求并通过引擎传递给下载器yield scrapy.Request(url="http://example.com", callback=self.parse)def parse(self, response):# 处理响应数据# 创建一个CrawlerProcess对象
from scrapy.crawler import CrawlerProcess
from scrapy.utils.project import get_project_settingsprocess = CrawlerProcess(settings=get_project_settings())# 启动引擎和下载器来处理请求和响应
with process:process.crawl(MySpider)process.start()

处理异常和重试机制:

在爬取过程中,可能会遇到各种异常情况,比如网络问题、页面不存在或服务器错误等。Scrapy引擎提供了异常处理和重试机制,确保爬取任务的顺利进行。以下是处理异常和重试的机制解释:

  1. 请求异常处理:如果在请求过程中发生异常(如网络错误),引擎会捕获异常并根据配置的策略来处理。可以配置引擎在发生异常时重新发送请求,或根据具体情况决定如何处理。

  2. 响应异常处理:如果在下载过程中发生异常(如服务器返回错误状态码),引擎会捕获异常并触发相应的事件和信号。可以注册处理函数来处理异常响应,比如重新发送请求或进行其他处理。

  3. 重试机制:当发生异常或其他情况导致请求或下载失败时,引擎可以根据配置的重试策略尝试重新发送请求或下载页面。可以设置重试次数和重试时间间隔来控制重试的行为。

  4. 引擎事件和信号:引擎提供了一系列的事件和信号,可以被注册的处理函数捕获和处理。可以根据具体的异常情况来注册相应的处理函数,以实现自定义的异常处理和重试逻辑。

案例解释:
import scrapyclass MySpider(scrapy.Spider):name = "myspider"def start_requests(self):# 生成初始请求并通过引擎传递给下载器yield scrapy.Request(url="http://example.com", callback=self.parse, errback=self.handle_error)def parse(self, response):# 处理响应数据def handle_error(self, failure):# 处理请求或下载异常# 判断是否继续重试if failure.request.meta.get('retry_times', 0) < self.max_retries:# 重新发送请求并通过引擎再次传递给下载器yield failure.request.replace(meta={'retry_times': failure.request.meta.get('retry_times', 0) + 1})else:# 达到重试次数上限,进行其他处理# 创建一个CrawlerProcess对象
from scrapy.crawler import CrawlerProcess
from scrapy.utils.project import get_project_settingsprocess = CrawlerProcess(settings=get_project_settings())# 启动引擎和下载器来处理请求和响应
with process:process.crawl(MySpider)process.start()

通过上述异常处理和重试机制,Scrapy引擎能够灵活处理各种异常情况,并根据需要进行相应的操作,确保爬取任务的成功完成。

总结:

        Scrapy引擎是Scrapy框架的核心,承担了整个爬虫流程的协调和管理任务。它的核心功能包括请求调度和管理、页面下载、数据提取和处理等。

        引擎通过调度器将请求发送给下载器,接收下载器返回的响应,并将响应传递给爬虫中的解析函数进行数据提取。同时,引擎支持扩展和中间件机制,允许开发者自定义请求和响应的处理流程。引擎还提供了事件和信号机制,使用户能够自定义触发和处理特定事件的逻辑。

总体而言,Scrapy引擎作为中心角色,通过协调各组件的工作,实现了高效、可定制的爬虫流程。同时,引擎支持并发处理多个请求和响应,并提供异常处理和重试机制,保证了爬取任务的正常进行。

这篇关于爬虫工作量由小到大的思维转变---<第五十章 Scrapy 深入理解Scrapy爬虫引擎(1)--核心功能>的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/842046

相关文章

【前端学习】AntV G6-08 深入图形与图形分组、自定义节点、节点动画(下)

【课程链接】 AntV G6:深入图形与图形分组、自定义节点、节点动画(下)_哔哩哔哩_bilibili 本章十吾老师讲解了一个复杂的自定义节点中,应该怎样去计算和绘制图形,如何给一个图形制作不间断的动画,以及在鼠标事件之后产生动画。(有点难,需要好好理解) <!DOCTYPE html><html><head><meta charset="UTF-8"><title>06

认识、理解、分类——acm之搜索

普通搜索方法有两种:1、广度优先搜索;2、深度优先搜索; 更多搜索方法: 3、双向广度优先搜索; 4、启发式搜索(包括A*算法等); 搜索通常会用到的知识点:状态压缩(位压缩,利用hash思想压缩)。

深入探索协同过滤:从原理到推荐模块案例

文章目录 前言一、协同过滤1. 基于用户的协同过滤(UserCF)2. 基于物品的协同过滤(ItemCF)3. 相似度计算方法 二、相似度计算方法1. 欧氏距离2. 皮尔逊相关系数3. 杰卡德相似系数4. 余弦相似度 三、推荐模块案例1.基于文章的协同过滤推荐功能2.基于用户的协同过滤推荐功能 前言     在信息过载的时代,推荐系统成为连接用户与内容的桥梁。本文聚焦于

Andrej Karpathy最新采访:认知核心模型10亿参数就够了,AI会打破教育不公的僵局

夕小瑶科技说 原创  作者 | 海野 AI圈子的红人,AI大神Andrej Karpathy,曾是OpenAI联合创始人之一,特斯拉AI总监。上一次的动态是官宣创办一家名为 Eureka Labs 的人工智能+教育公司 ,宣布将长期致力于AI原生教育。 近日,Andrej Karpathy接受了No Priors(投资博客)的采访,与硅谷知名投资人 Sara Guo 和 Elad G

C++11第三弹:lambda表达式 | 新的类功能 | 模板的可变参数

🌈个人主页: 南桥几晴秋 🌈C++专栏: 南桥谈C++ 🌈C语言专栏: C语言学习系列 🌈Linux学习专栏: 南桥谈Linux 🌈数据结构学习专栏: 数据结构杂谈 🌈数据库学习专栏: 南桥谈MySQL 🌈Qt学习专栏: 南桥谈Qt 🌈菜鸡代码练习: 练习随想记录 🌈git学习: 南桥谈Git 🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈�

让树莓派智能语音助手实现定时提醒功能

最初的时候是想直接在rasa 的chatbot上实现,因为rasa本身是带有remindschedule模块的。不过经过一番折腾后,忽然发现,chatbot上实现的定时,语音助手不一定会有响应。因为,我目前语音助手的代码设置了长时间无应答会结束对话,这样一来,chatbot定时提醒的触发就不会被语音助手获悉。那怎么让语音助手也具有定时提醒功能呢? 我最后选择的方法是用threading.Time

【生成模型系列(初级)】嵌入(Embedding)方程——自然语言处理的数学灵魂【通俗理解】

【通俗理解】嵌入(Embedding)方程——自然语言处理的数学灵魂 关键词提炼 #嵌入方程 #自然语言处理 #词向量 #机器学习 #神经网络 #向量空间模型 #Siri #Google翻译 #AlexNet 第一节:嵌入方程的类比与核心概念【尽可能通俗】 嵌入方程可以被看作是自然语言处理中的“翻译机”,它将文本中的单词或短语转换成计算机能够理解的数学形式,即向量。 正如翻译机将一种语言

【C++高阶】C++类型转换全攻略:深入理解并高效应用

📝个人主页🌹:Eternity._ ⏩收录专栏⏪:C++ “ 登神长阶 ” 🤡往期回顾🤡:C++ 智能指针 🌹🌹期待您的关注 🌹🌹 ❀C++的类型转换 📒1. C语言中的类型转换📚2. C++强制类型转换⛰️static_cast🌞reinterpret_cast⭐const_cast🍁dynamic_cast 📜3. C++强制类型转换的原因📝

深入手撕链表

链表 分类概念单链表增尾插头插插入 删尾删头删删除 查完整实现带头不带头 双向链表初始化增尾插头插插入 删查完整代码 数组 分类 #mermaid-svg-qKD178fTiiaYeKjl {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-

Spring框架5 - 容器的扩展功能 (ApplicationContext)

private static ApplicationContext applicationContext;static {applicationContext = new ClassPathXmlApplicationContext("bean.xml");} BeanFactory的功能扩展类ApplicationContext进行深度的分析。ApplicationConext与 BeanF