Scrapy中間件(Middleware)

Spider中間件(Middleware)

Spider中間件是介入到Scrapy的spider處理機制的鉤子框架,您能夠添加代碼來處理髮送給 Spiders的response及spider產生的item和request。html

激活spider中間件

要啓用spider中間件,您能夠將其加入到 SPIDER_MIDDLEWARES 設置中。 該設置是一個字典,鍵位中間件的路徑,值爲中間件的順序(order)。框架

樣例:dom

SPIDER_MIDDLEWARES = {
    'myproject.middlewares.CustomSpiderMiddleware': 543,
}

SPIDER_MIDDLEWARES 設置會與Scrapy定義的 SPIDER_MIDDLEWARES_BASE 設置合併(但不是覆蓋), 然後根據順序(order)進行排序,最後獲得啓用中間件的有序列表: 第一個中間件是最靠近引擎的,最後一箇中間件是最靠近spider的。scrapy

關於如何分配中間件的順序請查看 SPIDER_MIDDLEWARES_BASE 設置,然後根據您想要放置中間件的位置選擇一個值。 因爲每一箇中間件執行不一樣的動做,您的中間件可能會依賴於以前(或者以後)執行的中間件,所以順序是很重要的。ide

若是您想禁止內置的(在 SPIDER_MIDDLEWARES_BASE 中設置並默認啓用的)中間件, 您必須在項目的 SPIDER_MIDDLEWARES 設置中定義該中間件,並將其值賦爲 None 。 例如,若是您想要關閉off-site中間件:網站

SPIDER_MIDDLEWARES = {
    'myproject.middlewares.CustomSpiderMiddleware': 543,
    'scrapy.contrib.spidermiddleware.offsite.OffsiteMiddleware': None,
}

最後,請注意,有些中間件須要經過特定的設置來啓用。更多內容請查看相關中間件文檔。url

編寫您本身的spider中間件

編寫spider中間件十分簡單。每一箇中間件組件是一個定義瞭如下一個或多個方法的Python類:spa

classscrapy.contrib.spidermiddleware.SpiderMiddlewarecode

process_spider_input(responsespider)htm

當response經過spider中間件時,該方法被調用,處理該response。

process_spider_input() 應該返回 None 或者拋出一個異常。

若是其返回 None ,Scrapy將會繼續處理該response,調用全部其餘的中間件直到spider處理該response。

若是其跑出一個異常(exception),Scrapy將不會調用任何其餘中間件的process_spider_input() 方法,並調用request的errback。 errback的輸出將會以另外一個方向被從新輸入到中間件鏈中,使用 process_spider_output() 方法來處理,當其拋出異常時則帶調用 process_spider_exception() 。

參數:
  • response (Response 對象) – 被處理的response
  • spider (Spider 對象) – 該response對應的spider

process_spider_output(responseresultspider)

當Spider處理response返回result時,該方法被調用。

process_spider_output() 必須返回包含 Request 或 Item 對象的可迭代對象(iterable)。

參數:
  • response (Response 對象) – 生成該輸出的response
  • result (包含 Request 或 Item 對象的可迭代對象(iterable)) – spider返回的result
  • spider (Spider 對象) – 其結果被處理的spider

process_spider_exception(responseexceptionspider)

當spider或(其餘spider中間件的) process_spider_input() 跑出異常時, 該方法被調用。

process_spider_exception() 必需要麼返回 None , 要麼返回一個包含 Response 或 Item 對象的可迭代對象(iterable)。

若是其返回 None ,Scrapy將繼續處理該異常,調用中間件鏈中的其餘中間件的process_spider_exception() 方法,直到全部中間件都被調用,該異常到達引擎(異常將被記錄並被忽略)。

若是其返回一個可迭代對象,則中間件鏈的 process_spider_output() 方法被調用, 其餘的 process_spider_exception() 將不會被調用。

參數:
  • response (Response 對象) – 異常被拋出時被處理的response
  • exception (Exception 對象) – 被跑出的異常
  • spider (Spider 對象) – 拋出該異常的spider

process_start_requests(start_requestsspider)

0.15 新版功能.

該方法以spider 啓動的request爲參數被調用,執行的過程相似於 process_spider_output() ,只不過其沒有相關聯的response而且必須返回request(不是item)。

其接受一個可迭代的對象(start_requests 參數)且必須返回另外一個包含 Request 對象的可迭代對象。

註解

當在您的spider中間件實現該方法時, 您必須返回一個可迭代對象(相似於參數start_requests)且不要遍歷全部的 start_requests。 該迭代器會很大(甚至是無限),進而致使內存溢出。 Scrapy引擎在其具備能力處理start request時將會拉起request, 所以start request迭代器會變得無限,而由其餘參數來中止spider( 例如時間限制或者item/page記數)。

參數:
  • start_requests (包含 Request 的可迭代對象) – start requests
  • spider (Spider 對象) – start requests所屬的spider

內置spider中間件參考手冊

本頁面介紹了Scrapy自帶的全部spider中間件。

關於默認啓用的中間件列表(及其順序)請參考 SPIDER_MIDDLEWARES_BASE 設置。

DepthMiddleware

classscrapy.contrib.spidermiddleware.depth.DepthMiddleware

DepthMiddleware是一個用於追蹤每一個Request在被爬取的網站的深度的中間件。 其能夠用來限制爬取深度的最大深度或相似的事情。

DepthMiddleware 能夠經過下列設置進行配置(更多內容請參考設置文檔):

  • DEPTH_LIMIT - 爬取所容許的最大深度,若是爲0,則沒有限制。
  • DEPTH_STATS - 是否收集爬取狀態。
  • DEPTH_PRIORITY - 是否根據其深度對requet安排優先級

HttpErrorMiddleware

classscrapy.contrib.spidermiddleware.httperror.HttpErrorMiddleware

過濾出全部失敗(錯誤)的HTTP response,所以spider不須要處理這些request。 處理這些request意味着消耗更多資源,而且使得spider邏輯更爲複雜。

根據 HTTP標準 ,返回值爲200-300之間的值爲成功的resonse。

若是您想處理在這個範圍以外的response,您能夠經過 spider的 handle_httpstatus_list 屬性或HTTPERROR_ALLOWED_CODES 設置來指定spider能處理的response返回值。

例如,若是您想要處理返回值爲404的response您能夠這麼作:

class MySpider(CrawlSpider):
    handle_httpstatus_list = [404]

Request.meta 中的 handle_httpstatus_list 鍵也能夠用來指定每一個request所容許的response code。

不過請記住,除非您知道您在作什麼,不然處理非200返回通常來講是個糟糕的決定。

HttpErrorMiddleware settings

HTTPERROR_ALLOWED_CODES

默認: []

忽略該列表中全部非200狀態碼的response。

HTTPERROR_ALLOW_ALL

默認: False

忽略全部response,無論其狀態值。

OffsiteMiddleware

classscrapy.contrib.spidermiddleware.offsite.OffsiteMiddleware

過濾出全部URL不禁該spider負責的Request。

該中間件過濾出全部主機名不在spider屬性 allowed_domains 的request。

當spide返回一個主機名不屬於該spider的request時, 該中間件將會作一個相似於下面的記錄:

DEBUG: Filtered offsite request to 'www.othersite.com': <GET http://www.othersite.com/some/page.html>

爲了不記錄太多無用信息,其將對每一個新發現的網站記錄一次。所以,例如, 若是過濾出另外一個 www.othersite.com 請求,將不會有新的記錄。 但若是過濾出 someothersite.com 請求,仍然會有記錄信息(僅針對第一次)。

若是spider沒有定義 allowed_domains 屬性,或該屬性爲空, 則offsite 中間件將會容許全部request。

若是request設置了 dont_filter 屬性, 即便該request的網站不在容許列表裏,則offsite中間件將會容許該request。

RefererMiddleware

classscrapy.contrib.spidermiddleware.referer.RefererMiddleware

根據生成Request的Response的URL來設置Request Referer 字段。

RefererMiddleware settings

REFERER_ENABLED

0.15 新版功能.

默認: True

是否啓用referer中間件。

UrlLengthMiddleware

classscrapy.contrib.spidermiddleware.urllength.UrlLengthMiddleware

過濾出URL長度比URLLENGTH_LIMIT的request。

UrlLengthMiddleware 能夠經過下列設置進行配置(更多內容請參考設置文檔):

  • URLLENGTH_LIMIT - 容許爬取URL最長的長度.
相關文章
相關標籤/搜索