簡介
知乎用戶信息是很是大的,本文是一個scrapy實戰:怎樣抓取全部知乎用戶信息。 爬取的思路以下圖所示: java
- 選擇一個知乎用戶做爲根節點
- 每一個用戶都會有關注列表
- 選擇每個用戶的關注列表,進行遞歸爬取知乎用戶信息
站點分析
本文以輪子哥爲根節點(根節點能夠隨便選擇),打開輪子哥的關注列表,並翻頁查看關注列表: python
翻頁是一個AJAX請求,每頁20個關注用戶,而且有一些簡要的用戶信息 其中有一個是url-token,它是用來標識一個用戶的,在上面截圖中那個用戶的主頁url爲:www.zhihu.com/people/liu-… 其中就有url-token面試
項目實戰
建立項目redis
- scrapy startproject zhihuuser
- cd zhihuuser
- scrapy genspider zhihu www.zhihu.com 另外,在setting配置文件中有一個屬性 ROBOTSTXT_OBEY = False 咱們把它改成false,爲true可能受限於robottxt規則,導致一些網頁不能爬取,通常設置爲false 注意 訪問知乎時須要加useragent請求頭,不然會返回500狀態碼,這個的配置在setting文件中:
思路分析
獲取用戶信息 首先須要獲取用戶的基本信息,這個基本信息能夠經過請求相似下面的url得到: www.zhihu.com/people/{url… 而url_token能夠在用戶的關注列表中獲取,上面url的頁面相似於這個 json
另外,還有右側得到贊同、被收藏、感謝的次數 從上述url獲取用戶基本信息後,接下來就是獲取當前用戶的關注列表:
獲取用戶的關注列表 這個列表存在翻頁,通過分析得知關注列表的翻頁是經過AJAX請求實現的,獲取某頁關注列表url以下所示:
www.zhihu.com/api/v4/memb… 提取一下規律:
www.zhihu.com/api/v4/memb…{
url-token}/followees?include={include}&offset={offset}&limit=2{limit} 其中include爲: data[*].answer_count,articles_count,gender,follower_count,is_followed,is_following,badge[?(type=best_answerer)].topics 上面url返回時一個json,該json中包含了20個關注者,response數據以下圖所示:
對於一個關注者,咱們只須要獲取該用戶的
url-token*,經過url-token便可拼接出該用戶的主頁,也就能夠得到該用戶的基本信息,以及關注者列表等。 獲取到url-token後,咱們須要判斷有沒有下一頁,若是有則進行翻頁,在上圖的後半部分還有一個字段:
翻到當前的最後一頁,該字段以下圖所示:
所以依據is_end字段就能夠判斷是否下一頁關注者了,使用next字段的值便可獲取下一頁關注者的列表了。
思路整理
- 首先訪問一個知乎大V的主頁,並解析該大V的基本信息(parse_user);
- 以後,獲取該大V第一頁關注者列表(parse_follows)
- 依次獲取該頁關注者列表的url_token,進一步解析出列表中的全部關注者的基本信息
- 解析完當前頁的關注者基本信息後,進行分頁的判斷和處理:即獲取next字段的值,而後請求下一頁url,並回調當前函數進行解析
- 這樣作完後,咱們即完成了當前知乎大V的全部關注者基本信息的爬取,可是這樣作還徹底不夠,只解析了一個用戶的關注者,也就是咱們還要改解析當前用戶全部關注者的關注者的基本信息,這樣才能把知乎用戶鏈接起來,造成一個網。怎麼才能實現呢?
- 在parse_user中咱們解析到了當前用戶的基本信息,每解析一個關注者基本信息後,此還應該解析該用戶關注者列表,也就是在parse_user中也須要獲取url_token,沒有該值咱們就獲取不到用戶的關注列表。那麼如何在parse_user時獲取用戶的url_token呢?
- 實際上url_token在parse_user的response中已經包含了:即經過response得到當前頁面的url,當前頁面的url中就包含了當前用戶的url_token
因此呢?在解析用戶基本信息的同時,咱們能夠拿到用戶的url_token,進一步咱們也就能夠拿到該用戶的關注者列表,如此遞爬取,基本可得到全部知乎用戶的全部基本信息。api
- 另外,須要考慮去重問題:遞歸爬取不去重的話會形成死循環。去重最簡單的使用set:將解析過用戶的url_token放入到set中,在解析一個用戶基本信息前先判斷該用戶以前有沒有被解析過。可使用分佈式redis去重,單擊可能形成內存溢出,比較知乎用戶數量龐大
- 最後,爲了防止請求過多而被知乎封禁ip,可使用以前介紹的ip代理池,具體能夠看先前的文章 pipline設置
- 數據的存儲經過pipline設置便可 本次爬取的item數據結果以下圖所示:
本次的pipline設置爲:
源碼和爬取的部分數據:
爬取的部分知乎用戶數據 scrapy
源碼 爬取知乎用戶的思路已經在文章介紹了,思路理好後,實現比較塊。 主要是源碼有點長,這裏就不全貼出來了。須要源碼的同窗能夠經過文末方式獲取
掃描下方二維碼,發送關鍵詞「知乎」便可獲取本文的完整源碼和詳細程序註釋 分佈式
資料分享
java學習筆記、10T資料、100多個java項目分享ide
公衆號專一:互聯網求職面經、java、python、爬蟲、大數據等技術分享: 公衆號菜鳥名企夢
後臺發送「csdn」便可免費領取【csdn】和【百度文庫】下載服務; 公衆號菜鳥名企夢
後臺發送「資料」:便可領取5T精品學習資料、java面試考點和java面經總結,以及幾十個java、大數據項目,資料很全,你想找的幾乎都有函數