初識Scrapy,在充滿爬蟲的世界裡做一個好公民
歡迎來到你的Scrapy之旅。通過本文,我們旨在將你從一個只有很少經驗甚至沒有經驗的Scrapy初學者,打造成擁有信心使用這個強大的框架從網路或者其他源爬取大數據集的Scrapy專家。本文將介紹Scrapy,並且告訴你一些可以用它實現的很棒的事情。
1.1 初識Scrapy
Scrapy是一個健壯的網路框架,它可以從各種數據源中抓取數據。作為一個普通的網路用戶,你會發現自己經常需要從網站上獲取數據,使用類似Excel的電子表格程序進行瀏覽,以便離線訪問數據或者執行計算。而作為一個開發者,你需要經常整合多個數據源的數據,但又十分清楚獲得和抽取數據的複雜性。無論難易,Scrapy都可以幫助你完成數據抽取的行動。
以健壯而又有效的方式抽取大量數據,Scrapy已經擁有了多年經驗。使用Scrapy,你只需一個簡單的設置,就能完成其他爬蟲框架中需要很多類、插件和配置項才能完成的工作。
從開發者的角度來說,你也會十分欣賞Scrapy的基於事件的架構。它允許我們將數據清洗、格式化、裝飾以及將這些數據存儲到資料庫中等操作級聯起來,只要我們操作得當,性能降低就會很小。在本文中,你將學會怎樣可以達到這一目的。從技術上講,由於Scrapy是基於事件的,這就能夠讓我們在擁有上千個打開的連接時,可以通過平穩的操作拆分吞吐量的延遲。來看這樣一個極端的例子,假設你需要從一個擁有匯總頁的網站中抽取房源,其中每個匯總頁包含100個房源。Scrapy可以非常輕鬆地在該網站中並行執行16個請求,假設完成一個請求平均需要花費1秒鐘的時間,你可以每秒爬取16個頁面。如果將其與每頁的房源數相乘,可以得出每秒將產生1600個房源。想像一下,如果每個房源都必須在大規模並行雲存儲當中執行一次寫入,每次寫入平均需要耗費3秒鐘的時間(非常差的主意)。為了支持每秒16個請求的吞吐量,就需要我們並行運行1600 × 3 = 4800次寫入請求。對於一個傳統的多線程應用而言,則需要轉變為4800個線程,無論是對你,還是對操作系統來說,這都會是一個非常糟糕的體驗。而在Scrapy的世界中,只要操作系統沒有問題,4800個並發請求就能夠處理。此外,Scrapy的內存需求和你需要的房源數據量很接近,而對於多線程應用而言,則需要為每個線程增加與房源大小相比十分明顯的開銷。
簡而言之,緩慢或不可預測的網站、資料庫或遠程API都不會對Scrapy的性能產生毀滅性的結果,因為你可以並行運行多個請求,並通過單一線程來管理它們。這意味著更低的主機託管費用,與其他應用的協作機會,以及相比於傳統多線程應用而言更簡單的代碼(無同步需求)。
1.2 喜歡Scrapy的更多理由
Scrapy已經擁有超過5年的歷史了,成熟而又穩定。除了上一節中提到的性能優勢外,還有下面這些能夠讓你愛上Scrapy的理由。
- Scrapy能夠識別殘缺的HTML
你可以在Scrapy中直接使用Beautiful Soup或lxml,不過Scrapy還提供了一種在lxml之上更高級的XPath(主要)介面——selectors。它能夠更高效地處理殘缺的HTML代碼和混亂的編碼。
- 社區
Scrapy擁有一個充滿活力的社區。只需要看看https://groups. http://google.com/ forum/#!forum/scrapy-users 上的郵件列表,以及Stack Overflow網站(http:// http://stackoverflow.com/questions/tagged/ scrapy)中的上千個問題就可以知道了。大部分問題都能夠在幾分鐘內得到回應。更多社區資源可以從http://scrapy.org/ community/中獲取到。
- 社區維護的組織良好的代碼
Scrapy要求以一種標準方式組織你的代碼。你只需編寫被稱為爬蟲和管道的少量Python模塊,並且還會自動從引擎自身獲取到未來的任何改進。如果你在網上搜索,可以發現有相當多專業人士擁有Scrapy經驗。也就是說,你可以很容易地找到人來維護或擴展你的代碼。無論是誰加入你的團隊,都不需要漫長的學習曲線,來理解你的自定義爬蟲中的特別之處。
- 越來越多的高質量功能
如果你快速瀏覽發布日誌(http://doc.scrapy.org/en/latest/ news.html),就會注意到無論是在功能上,還是在穩定性/bug修復上,Scrapy都在不斷地成長。
1.3 掌握自動化數據爬取的重要性
對於大多數人來說,掌握一門像Scrapy這樣很酷的技術所帶來的好奇心和精神上的滿足,足以激勵我們。令人驚喜的是,在學習這個優秀框架的同時,我們還能享受到開發過程始於數據和社區,而不是代碼所帶來的好處。
1.3.1 開發健壯且高質量的應用,並提供合理規劃
為了開發現代化的高質量應用,我們需要真實的大數據集,如果可能的話,在開始動手寫代碼之前就應該進行這一步。現代化軟體開發就是實時處理大量不完善數據,並從中提取出知識和有價值的情報。當我們開發軟體並應用於大數據集時,一些小的錯誤和疏忽難以被檢測出來,就有可能導致昂貴的錯誤決策。比如,在做人口統計學研究時,很容易發生僅僅是由於州名過長導致數據被默認丟棄,造成整個州的數據被忽視的錯誤。在開發階段,甚至更早的設計探索階段,通過細心抓取,並使用具有生產質量的真實世界大數據集,可以幫助我們發現和修復錯誤,做出明智的工程決策。
另外一個例子是,假設你想要設計Amazon風格的「如果你喜歡這個商品,也可能喜歡那個商品」的推薦系統。如果你能夠在開始之前,先爬取並收集真實世界的數據集,就會很快意識到有關無效條目、停產商品、重複、無效字元以及偏態分布引起的性能瓶頸等問題。這些數據將會強迫你設計足夠健壯的演算法,無論是數千人購買過的商品,還是零銷售量的新條目,都能夠很好地處理。而孤立的軟體開發,可能會在幾個星期的開發之後,也要面對這些醜陋的真實世界數據。雖然這兩種方法最終可能會收斂,但是為你提供進度預估承諾的能力以及軟體的質量,都將隨著項目進展而產生顯著差別。從數據開始,能夠帶給我們更加愉悅並且可預測的軟體開發體驗。
1.3.2 快速開發高質量最小可行產品
對於初創公司而言,大規模真實數據的集甚至更加必要。你可能聽說過「精益創業」,這是由Eric Ries創造的一個術語,用於描述類似技術初創公司這樣極端不確定條件下的業務發展過程。該框架的一個關鍵概念是最小可行產品(Minimum Viable Product,MVP),這種產品只有有限的功能,可以被快速開發並向有限的客戶發布,用於測試反響及驗證業務假設。基於獲得的反饋,初創公司可能會選擇繼續更進一步的投資,也可能是轉向其他更有前景的方向。
在該過程中的某些方面,很容易忽視與數據緊密連接的問題,這正是Scrapy所能為我們做的部分。比如,當邀請潛在的客戶嘗試使用我們的手機應用時,作為開發者或企業主,會要求他們評判這些功能,想像應用在完成時看起來應該如何。對於這些並非專家的人而言,這裡需要的想像有可能太多了。這個差距相當於一個應用只展示了「產品1」、「產品2」、「用戶433」,而另一個應用提供了「三星 UN55J6200 55英寸電視機」、用戶「Richard S」給出了五星好評以及能夠讓你直達產品詳情頁面(儘管事實上我們還沒有寫這個頁面)的有效鏈接等諸多信息。人們很難客觀判斷一個MVP產品的功能性,除非使用了真實且令人興奮的數據。
一些初創企業將數據作為事後考慮的原因之一是認為收集這些數據需要昂貴的代價。的確,我們通常需要開發表單及管理界面,並花費時間錄入數據,但我們也可以在編寫代碼之前使用Scrapy爬取一些網站。
1.3.3 Google不會使用表單,爬取才能擴大規模
當談及表單時,讓我們來看下它是如何影響產品增長的。想像一下,如果Google的創始人在創建其引擎的第一個版本時,包含了一個每名網站管理員都需要填寫的表單,要求他們把網站中每一頁的文字都複製粘貼過來。然後,他們需要接受許可協議,允許Google處理、存儲和展示他們的內容,並剔除大部分廣告利潤。你能想像解釋該想法並說服人們參與這一過程所需花費的時間和精力會有多大嗎?即使市場非常渴望一個優秀的搜索引擎(事實正是如此),這個引擎也不會是Google,因為它的增長過於緩慢。即使是最複雜的演算法,也不能彌補數據的缺失。Google使用網路爬蟲技術,在頁面間跳轉鏈接,填充其龐大的資料庫。網站管理員則不需要做任何事情。實際上,反而還需要一些努力才能阻止Google索引你的頁面。
雖然Google使用表單的想法聽起來有些荒謬,但是一個典型的網站需要用戶填寫多少表單呢?登錄表單、新房源表單、結賬表單,等等。這些表單中有多少會阻礙應用增長呢?如果你充分了解你的受眾/客戶,很可能已經擁有關於他們通常使用並且很可能已經有賬號的其他網站的線索了。比如,一個開發者很可能擁有Stack Overflow和GitHub的賬號。那麼,在獲得他們允許的情況下,你是否能夠抓取這些站點,只需他們提供給你用戶名,就能自動填充照片、簡介和一小部分近期文章呢?你能否對他們最感興趣的一些文章進行快速文本分析,並根據其調整網站的導航結構,以及建議的產品和服務呢?我希望你能夠看到如何使用自動化數據抓取替代表單,從而更好地服務你的受眾,增長網站規模。
1.3.4 發現並融入你的生態系統
抓取數據自然會讓你發現並考慮與你付出相關的社區的關係。當你抓取一個數據源時,很自然地就會產生一些問題:我是否相信他們的數據?我是否相信獲取數據的公司?我是否需要和他們溝通以獲得更正式的合作?我和他們是競爭關係還是合作關係?從其他源獲得這些數據會花費我多少錢?無論如何,這些商業風險都是存在的,不過抓取過程可以幫助我們儘早意識到這些風險,並制定出緩解策略。
你還會發現自己想知道能夠為這些網站和社區帶來的回饋是什麼。如果你能夠給他們帶來免費的流量,他們應該會很高興。另一方面,如果你的應用不能給你的數據源帶來一些價值,那麼你們的關係可能會很短暫,除非你與他們溝通,並找到合作的方式。通過從不同源獲取數據,你需要準備好開發對現有生態系統更友好的產品,充分尊重已有的市場參與者,只有在值得努力時才可以去破壞當前的市場秩序。現有的參與者也可能會幫助你成長得更快,比如你有一個應用,使用兩到三個不同生態系統的數據,每個生態系統有10萬個用戶,你的服務可能最終將這30萬個用戶以一種創造性的方式連接起來,從而使每個生態系統都獲益。例如,你成立了一個初創公司,將搖滾樂與T恤印花社區關聯起來,你的公司最終將成為兩種生態系統的融合,你和相應的社區都將從中獲益並得以成長。
1.4 在充滿爬蟲的世界裡做一個好公民
當開發爬蟲時,還有一些事情需要清楚。不負責任的網路爬蟲會令人不悅,甚至在某些情況下是違法的。有兩個非常重要的事情是避免類似拒絕服務(DoS)攻擊的行為以及侵犯版權。
對於第一種情況,一個典型的訪問者可能每幾秒訪問一個新的頁面。而一個典型的網路爬蟲則可能每秒下載數十個頁面。這樣就比典型用戶產生的流量多出了10倍以上。這可能會使網站所有者非常不高興。請使用流量限速將你產生的流量減少到可以接受的普通用戶的水平。此外,還應該監控響應時間,如果發現響應時間增加了,就需要降低爬蟲的強度。好消息是Scrapy對於這些功能都提供了開箱即用的實現。
對於版權問題,顯然你需要看一下你抓取的每個網站的版權聲明,並確保你理解其允許做什麼,不允許做什麼。大多數網站都允許你處理其站點的信息,只要不以自己的名義重新發布即可。在你的請求中,有一個很好的User-Agent
欄位,它可以讓網站管理員知道你是誰,你用他們的數據做什麼。Scrapy在製造請求時,默認使用BOT_NAME
參數作為User-Agent
。如果User-Agent
是一個URL或者能夠指明你的應用名稱,那麼網站管理員可以通過訪問你的站點,更多地了解你是如何使用他們的數據的。另一個非常重要的方面是,請允許任何網站管理員阻止你訪問其網站的指定區域。對於基於Web標準的robots.txt
文件(參見http://www.google.com/robots.txt的文件示例),Scrapy提供了用於尊重網站管理員設置的功能(RobotsTxtMiddleware
)。最後,最好向網站管理員提供一些方法,讓他們能說明不希望在你的爬蟲中出現的東西。至少網站管理員必須能夠很容易地找到和你交流及表達顧慮的方式。
1.5 Scrapy不是什麼
最後,很容易誤解Scrapy可以為你做什麼,主要是因為數據抓取這個術語與其相關術語有些模糊,很多術語是交替使用的。我將嘗試使這些方面更加清楚,以防止混淆,為你節省一些時間。
Scrapy不是Apache Nutch,也就是說,它不是一個通用的網路爬蟲。如果Scrapy訪問一個一無所知的網站,它將無法做出任何有意義的事情。Scrapy是用於提取結構化信息的,需要人工介入,設置合適的XPath或CSS表達式。而Apache Nutch則是獲取通用頁面並從中提取信息,比如關鍵字。它可能更適合於一些應用,但對另一些應用則又更不適合。
Scrapy不是Apache Solr、Elasticsearch或Lucene,換句話說,就是它與搜索引擎無關。Scrapy並不打算為你提供包含「Einstein」或其他單詞的文檔的參考。你可以使用Scrapy抽取數據,然後將其插入到Solr或Elasticsearch當中,我們會在第9章的開始部分講解這一做法,不過這僅僅是使用Scrapy的一個方法,而不是嵌入在Scrapy內的功能。
最後,Scrapy不是類似MySQL、MongoDB或Redis的資料庫。它既不存儲數據,也不索引數據。它只用於抽取數據。即便如此,你可能會將Scrapy抽取得到的數據插入到資料庫當中,而且它對很多資料庫也都有所支持,能夠讓你的生活更加輕鬆。然而Scrapy終究不是一個資料庫,其輸出也可以很容易地更改為只是磁碟中的文件,甚至什麼都不輸出——雖然我不確定這有什麼用。
本文摘自《精通Python爬蟲框架Scrapy》
《精通Python爬蟲框架Scrapy》
【美】迪米特里奧斯 考奇斯-勞卡斯(Dimitrios Kouzis-Loukas)箸
點擊封面購買紙書
Python3 scrapy教程,全面剖析網路爬蟲技術的實現原理,通過爬取示例演示Scrapy的應用,涵蓋從桌面端爬取到移動端爬取,實時爬取在內的所有內容。
本書講解了Scrapy的基礎知識,討論了如何從任意源提取數據,如何清理數據,以及如何使用Python和第三方API進行處理,以滿足自身需求。本書還講解了如何將爬取的數據高效地饋入資料庫、搜索引擎和流數據處理系統(比如Apache Spark)。在學習完本書後,你將對數據爬取胸有成竹,並將數據應用在自己的應用程序中。
延伸推薦
點擊關鍵詞閱讀更多新書:
Python|機器學習|Kotlin|Java|移動開發|機器人|有獎活動|Web前端|書單
在「非同步圖書」後台回復「關注」,即可免費獲得2000門在線視頻課程;推薦朋友關注根據提示獲取贈書鏈接,免費得非同步圖書一本。趕緊來參加哦!
掃一掃上方二維碼,回復「關注」參與活動!
推薦閱讀:
※python爬取QQ音樂
※python中 if-else 與 try-except的轉換 與while 與 whileTrue-try-except的轉換
※利用requests爬取表情包
※輪帶逛終極版! 抓取輪子哥(vczh)全部知乎動態
※愛奇藝人物信息scrapy-redis