第五章 動態網頁的挑戰
很多網站的數據,比如電商網站商品的價格,評論等等會採用動態加載的方式來加載,這樣可能在爬蟲程序剛剛訪問時無法直接獲取到相關數據。那麼怎麼應對這樣的問題呢?
5.1 動態網頁的使用場景
先看下面一個例子:
這是京東上看一本書的場景。我們發現打開一本書之後,書的價格,排名等信息及書的評論信息不是在我們第一次打開網站時就立即加載進來的。而是通過二次請求或多次的異步請求獲取的。這樣的頁面就是動態頁面。
關於動態頁面使用的場景:
希望異步刷新的場景。有些網頁內容很多,一次加載完對服務器壓力很大,而且有的用戶不會去查看所有內容;
5.2 回到與HTTP服務器發送請求數據的原始方法
5.2.1 GET方法
GET把參數數據隊列添加到URL中,Key和Value的各個字段一一對應;在URL中可以看到。
瀏覽器的URL中有些符號,字符不能被很好的識別。那麼我們需要有一套編碼的方式來傳遞信息。所以發送端需要做urlencode; 接收端需要做urldecode;1.https://www.baidu.com/s?wd=DNS
?xxx=yyy&time=zzz get 請求的標識
2.http://acb.com/login?name=zhangsan&password=123
login: name=zhangsan password=123
示例代碼:SpiderCodes\\baiduSearchp2.py
SpiderCodes\\baiduSearchp3.
5.2.2 POST方法
通過一個例子來看POST方法的使用:
這是有道翻譯的頁面,仔細觀察會發現,當用戶每次輸入一個想要翻譯的詞語時,頁面的URL信息並不發生任何改變。這是一個典型的異步使用Ajax的技術,用JSON格式進行數據的傳遞。
我們如何利用爬蟲程序來實現一個自己的翻譯器呢?
來看代碼示例:SpiderCodes\\youdaofanyip2.py5.3 更加難以對付的動態網站
5.3.1 應對需要多次數據的交互模擬的網站
我們有時會遇到像淘寶這樣的大型網站,對數據版權看得特別重的,它們的網站有大量的工程師和技術人員去維護,它們也可能在技術手段上採用多次交互數據包的方式來完成網站服務器與用戶瀏覽器之間的交互。如果此時還採用傳統的分析數據包的方式會比較的複雜,難度較高。那麼,有沒有一勞永逸的方法,來解決此類問題呢?
我們的解決方案是:Selenium + PhantomJS。
我們的爬蟲其實就是在做模擬瀏覽器的行為。
5.3.2 Selenium
一個Web自動化測試工具,最初是為了網站自動化測試而開發的;我們玩遊戲有按鍵精靈;Selenium也可以做類似的事情,但是它是在瀏覽器中做這樣的事情。
安裝: sudo pip install selenium(pip install selenium)
在Python中 from selenium import webdriver 來測試是否裝好
說明:想要用Python做自動化測試的童鞋們可以好好研究一下Selenium的使用。
5.3.3 PhantomJS
一個基於webkit無界面(headless)的瀏覽器,它可以把網站加載到內存中並執行頁面上的JS,但它沒有圖形用戶界面,所以耗費的資源比較少;
安裝: sudo apt install phantomjs (此方法可能安裝不完整,導致部分功能無法使用)
Linux Ubuntu下完全安裝的方法(參看http://blog.csdn.net/m0_38124502/article/details/79276499
)
Wget
https://bitbucket.org/ariya/phantomjs/downloads/phantomjs-2.1.1-linux-x86_64.tar.bz2
cd 下載
tar -xvf phantomjs-2.1.1-linux-x86_64.tar.bz2
cd phantomjs-2.1.1-linux-x86_64/
cd bin/
sudo cp phantomjs /usr/bin
python -啟動-> 瀏覽器進程phantomjs,
測試:
SpiderCodes\\Phantomjs\\.. 對其中的例子helloworld.js, pageload.js
進行測試;
注意: ****有可能造成資源洩漏;為了避免這種事的發生,需要有個策略適當的時候去kill phantomjs進程。
5.3.4 Selenium + PhantomJS
雙劍合璧利用二者同時完成某個任務,示例代碼如下:
SpiderCodes\\testPhantomJS.py
5.4 關於動態網站信息抓取的總結
總的來說,我們的爬蟲要儘量模擬的看起來就像是真正的用戶在瀏覽器上訪問服務器網站的行為。如果我們使用GET或POST的方式來模擬瀏覽器與服務器間通信的行為,成本比較低,但是應對複雜的網站或者服務器精心防禦的網站來說是很難騙過服務器的。Selenim+PhantomJS的方案則會讓我們的程序看起來更像是普通的用戶,但是它的效率相對而言會降低很多,速度也會慢很多。在大規模爬去數據時可能遇到許多新的挑戰。(比如網站尺寸的設置,等待時間的設定等)
練習: 抓取貓眼電影 http://maoyan.com/board/4?offset 中TOP100的電影榜單;
閱讀更多 小悅 的文章