網站首頁 編程語言 正文
Scrapy的中間件分為Download Middleware和Spider Middleware
下載中間件,他是處于Request和Response中間的處理模塊
Scheduler調度器從隊列中拿出一個Request發送給Downloader執行下載,這個過程會經過Downloader Middleware的處理。另外,當Downloader將Request下載完成得到Response返回給Spider時會再次經過Downloader Middleware處理。所以整個架構中Download Middleware能起到的作用有以下兩個
在Request執行下載之前,對我們的Request請求進行修改
下載后生成的Response發送給Spider之前,也就是我們可以在生成Resposne被Spider解析之前對其進行修改
Downloader Middleware的功能十分強大,修改User-Agent、處理重定向、設置代理、失敗重試、設置Cookies等功能都需要借助它來實現。
一、說明
需要說明的是,Scrapy其實已經提供了許多Downloader Middleware,比如負責失敗重試、自動重定向等功能的Middleware,它們被DOWNLOADER_MIDDLEWARES_BASE變量所定義。
DOWNLOADER_MIDDLEWARES_BASE變量的內容如下所示:
'scrapy.downloadermiddlewares.robotstxt.RobotsTxtMiddleware': 100,
'scrapy.downloadermiddlewares.httpauth.HttpAuthMiddleware': 300,
'scrapy.downloadermiddlewares.downloadtimeout.DownloadTimeoutMiddleware': 350,
'scrapy.downloadermiddlewares.defaultheaders.DefaultHeadersMiddleware': 400,
'scrapy.downloadermiddlewares.useragent.UserAgentMiddleware': 500,
'scrapy.downloadermiddlewares.retry.RetryMiddleware': 550,
'scrapy.downloadermiddlewares.ajaxcrawl.AjaxCrawlMiddleware': 560,
'scrapy.downloadermiddlewares.redirect.MetaRefreshMiddleware': 580,
'scrapy.downloadermiddlewares.httpcompression.HttpCompressionMiddleware': 590,
'scrapy.downloadermiddlewares.redirect.RedirectMiddleware': 600,
'scrapy.downloadermiddlewares.cookies.CookiesMiddleware': 700,
'scrapy.downloadermiddlewares.httpproxy.HttpProxyMiddleware': 750,
'scrapy.downloadermiddlewares.stats.DownloaderStats': 850,
'scrapy.downloadermiddlewares.httpcache.HttpCacheMiddleware': 900,
這是一個字典格式,字典的鍵名是Scrapy內置的Downloader Middleware的名稱,鍵值代表了調用的優先級,數字小的Downloader Middleware會被優先調用。
如果向己定義Downloader Middleware要添加到項目里,DOWNLOADER_MIDDLEWARES_BASE變量不能直接修改。Scrapy提供了另外一個設置變量DOWNLOADER_MIDDLEWARES,我們直接修改這個變盤就可以添加向己定義的Downloader Middleware,以及禁用DOWNLOADER_MIDDLEWARES_BASE里面定義的Downloader Middleware
二、中間件方法
Scrapy內置的Downloader Middleware為Scrapy提供了基礎的功能,但在項目實戰中我們往往需要單獨定義Downloader Middleware。不用擔心,這個過程非常簡單,我們只需要實現某幾個方法即可。每個Downloader Middleware都定義了一個或多個方法的類,核心的方法有如下三個。
process_request(request, spider)
process_response(request, response, spider)
process_exception(request, exception, spider)
我們只需要實現至少一個方法,就可以定義一個Downloader Middleware。下面我們來看看這三個方法的詳細用法:
2.1、process_request(request, spider)
Request被Scrapy引擎調度給Downloader之前,process_request()方法就會被調用,也就是在Request從隊列里調度出來到Downloader下載執行之前,我們都可以用processrequest()方法對Request進行處理。方法的返回值必須為None、Response對象、Request對象之一,或者拋出IgnoreRequest異常
兩個參數:
request #是Request對象,即被處理的Request。
spider #是Spdier對象,即此Request對應的Spider。
返回None,Scrapy將繼續處理該request,執行其他中間件中的相應方法,直到合適的下載器處理函數被調用
返回為Response對象時,更低優先級的Downloader Middleware的process_request()和process_exception()方法就不會被繼續調用,每個Downloader Middleware的process_response()方法轉而被依次調用。調用完畢之后,直接將Response對象發送給Spider來處理。
當返回為Request對象時,更低優先級的Downloader Middleware的process_request()方法會停止執行。這個Request會重新放到調度隊列里,其實它就是一個全新的Request,等待被調度。如果被Scheduler調度了,那么所有的Downloader Middleware的process_request()方法會被重新按照順序執行。(不再使用之前的request對象去下載數據,而是根據現在返回的request對象返回數據,接著執行其他下載器處理函數。)
如果IgnoreRequest異常拋出,則所有的Downloader Middleware的process_exception()方法會依次執行。如果沒有一個方法處理這個異常,那么Request的errorback()方法就會回調。如果該異常還沒有被處理,那么它便會被忽略。(如果這個方法中拋出了異常,則會調用process_exception方法。)
2.2、process_response(request, response, spider)
Downloader執行Request下載之后,會得到對應的Response。Scrapy引擎便會將Response發送給Spider進行解析。在發送之前,我們都可以用process_response()方法來對Response進行處理。方法的返回值必須為Request對象、Response對象之一,或者拋出IgnoreRequest異常。
process_response()方法的參數有如下三個:
request #是Request對象,即此Response對應的Request。
response #是Response對象,即此被處理的Response。
spider #是Spider對象,即此Response對應的Spider。
2.3、process_exception(request, exception, spider)
當Downloader或process_request()方法拋出異常時,例如拋出IgnoreRequest異常,process_exception()方法就會被調用。方法的返回值必須為None、Response對象、Request對象之一。
process_exception()方法的參數有如下三個。
request #是Request對象,即產生異常的Request。
exception #是Exception對象,即拋出的異常。
spdier #是Spider對象,即Request對應的Spider。
原文鏈接:https://blog.csdn.net/weixin_43903639/article/details/122816105
- 上一篇:Django-跨域問題Csrf
- 下一篇:Headless Chrom自動化工具詳解
相關推薦
- 2022-01-17 rabbitmq出現 已安裝 rabbitmq-server 軟件包 post-installati
- 2022-06-08 FreeRTOS實時操作系統支持時間片示例詳解_操作系統
- 2022-06-22 c++分離講解模板的概念與使用_C 語言
- 2022-07-08 C語言完整實現12種排序算法(小結)_C 語言
- 2023-03-18 pandas預處理部分地區數據案例_python
- 2022-03-14 npm 依賴下載報錯 Hostname/IP does not match certificate‘
- 2022-12-12 python?打印完整異常問題_python
- 2022-09-20 Python?pip超詳細教程之pip的安裝與使用_python
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支