前言
首先我們看一下scrapy架構,
一,分布式爬蟲原理:
scrapy爬蟲分三大步:
- 第一步,獲取url,並生成requests
- 第二步,spider將requests通過引擎,給調度器,調度器將requests放入隊列中,等待下載器來取,下載器下載頁面后,返回response
- 第三步,spider獲取到下載器給的response,解析,存儲。
如果我們想進一步提高scrapy的爬取效率,在這三大步中,第一步第三步速度很快,大部分時間是浪費在第二步,只有提高下載器的下載速度才能提高爬取效率。如果兩個Scheduler同時從隊列里面取 Request ,每個Scheduler 都有其對應的 Downloader,那么
在帶寬足夠、正常爬取且不考慮隊列存取壓力的情況下, 爬取效率會有什么 ?沒錯,爬取效率會翻倍。
這樣, Scheduler可以擴展多個,Downloader 也可以擴展多個, 而爬取隊列Queue必須始終為1個,也就是所謂的共享爬取隊列。 這樣才能保證 Scheduer 從隊列里調度某個Queue之后,其他 Scheduler 不會重復調度此 Request ,就可以做到多個 Schduler 同步爬取 這就是分布式爬蟲的基本雛形
二,redis數據庫:
多台主機協同爬取的前提是共享爬取隊列,我們將共享爬取隊列放入數據庫中,方便多台主機同時獲取requests,而選擇redis數據庫主要是以下三個原因。
- 維護爬取隊列,分布式爬蟲的requests隊列是存在於redis數據庫中,redis數據庫是基於內存存儲的數據庫,存取效率高。
- 去重問題,既去掉Queue重復的requests,避免重復下載,redis數據庫有集合的存儲數據結構。每台主機生成的request,和redis數據庫中的requests指紋對比,沒有的話,就加入集合,有的話,就舍棄掉。
- 防止中斷,requests隊列是放在數據庫中的,爬蟲停止后,重新爬取,會按着原來爬取的隊列接着爬取,而不是重新爬取。
三,分布式爬蟲實現
實現分布式爬蟲,首先實現一個共享的爬取隊列,還要實現去重的功能,另外,重寫一個 Scheduer ,使之可以從共享的爬取隊列存取 Request。這些功能前人幫我們實現好了,就是Scrapy-Redis的python包。我們只需要導入直接用就可以了。