利用selenium爬取大眾點評網的商戶信息

利用selenium爬取大眾點評網的商戶信息

1 人贊了文章

最近在自學python,一方面是mark下自己的學習歷程,一方面也是分享下自己的心得體會,希望和我一樣自學爬蟲的小夥伴們能少走彎路,對,與君共勉!

那麼我們開始正題,首先說下幾個關鍵點(劃重點啦,敲黑板!):

1、為什麼用selenium?

因為通過requests.get()你會發現我們想爬取的商戶信息並不在response.text里,說明大眾網做了處理,原始的HTML代碼里沒有商戶信息,商戶信息應該是由JavaScript生成的,所以就得用selenium來驅瀏覽器載入網頁信息。

2、不要直接爬取商戶列表頁,而要從首頁進入

如果是我一樣,沒有代理IP池,就一個本機IP,那麼建議不要直接爬商戶列表頁,因為很容易被封。。。我們要從首頁進入,就像普通人正常瀏覽一樣,這樣就不會被封啦!

被大眾網ban了。。。

3、解析庫的選擇:建議使用scrapy

Scrapy的Selector模塊可以在Scrapy之外獨立使用,構造一個Selector對象,就可以實現XPath、CSS選擇器、正則表達式的三種混合解析,十分強大,強烈推薦!下面舉個栗子,可以感受一下。

from scrapy import Selectorhtml = <html><head><title>Example website</title></head><body><div id="context"><a href="context1.html">Context 1<br /><image src="image1_jpg" /></a><a href="context2.html">Context 3<br /><image src="image2_jpg" /></a><a href="context3.html">Context 3<br /><image src="image3_jpg" /></a></div></body></html>selector = Selector(text=html)items = selector.css(a).xpath(.//image/@src).re((.*?)_jpg)print(items)

接下來說下我的爬取思路:

步驟1:從首頁開始

找到搜索輸入框的網頁元素節點,模擬輸入『火鍋』關鍵字,模擬按下回車鍵,這樣就進入了商戶列表頁

首頁的banner

步驟2:進入商戶列表頁,爬取商戶信息

細節1:我的Chrome是通過新標籤頁打開商戶列表頁,所以要切換window的handler,否則後續循環遍歷爬取時的網址是首頁 ,而不是列表頁。

細節2:不要著急上來就爬

首先通過wait.until(EC.text_to_be_present_in_element())來校驗下當前頁碼是否和要爬取的頁碼一致

其次通過wait.until(EC.presence_of_element_located())來等待商戶信息塊的節點都載入出來了,以保證爬取成功率。

商戶列表信息

步驟3:跳轉至下一頁

定位到「下一頁」按鈕元素,以及判斷當前頁碼是否要爬取的最後一頁,如果不是,則觸發「下一頁」按鈕。

下一頁

步驟4:循環往複步驟2-3,直至結束

最後貼上運行效果、完整代碼:

平台環境:win7,語言:Python,IDE:Geany

程序運行效果截圖

from selenium import webdriverfrom selenium.webdriver.common.by import Byfrom selenium.webdriver.common.keys import Keysfrom selenium.webdriver.support.wait import WebDriverWaitfrom selenium.webdriver.support import expected_conditions as ECfrom selenium.common.exceptions import TimeoutExceptionfrom scrapy import Selector# 聲明一個Chrome瀏覽器對象browser = webdriver.Chrome()# 設置顯式等待時長(最長等待30秒,如果超過30秒還沒載入出來,就拋出異常)wait = WebDriverWait(browser, 30)# 大眾點評網地址URL = https://www.dianping.com/# 搜索關鍵字KEYWORD = 火鍋# 設置要爬取的商戶索引頁數MAX_PAGE = 10# 輸出列印格式 SHOW =
店名:{}

地址:{} + *7 + 商圈範圍:{}

級別:{} + *8 + 大眾網點評數:{} + *8 + 消費:{}
def index_page(page): """ 函數:商戶索引頁 參數:頁碼 """ print(
正在爬取第, page, 頁
) try: # 判斷當前高亮的頁碼數是否為當前要爬取的頁碼數,以保證成功跳轉到要爬取的頁面。 # text_to_be_present_in_element,它會等待指定的節點出現指定的文本,如果出現了即返回成功,否則拋出超時異常 wait.until(EC.text_to_be_present_in_element((By.XPATH, //div[@class="page"]//a[@class="cur"]), str(page))) # 判斷對應商戶列表信息的節點是否已經載入出來了,以保證接下來解析的有效性。 wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, .shop-wrap .shop-list.J_shop-list.shop-all-list))) # 解析並列印輸出商戶信息 for item in get_merchant(): print(* * 70) print(SHOW.format(item[shop], item[location], item[region], item[level], item[comment],item[consume])) # 判斷當前頁數是否要爬取的最後一頁 if page != MAX_PAGE: # 獲取下一頁按鈕 submit = wait.until(EC.element_to_be_clickable((By.CLASS_NAME, next))) # 點擊進入下一頁 submit.click() except TimeoutException: # 拋出超時異常,則重新爬取 index_page(page)def get_merchant(): 函數:獲取商戶信息 參數:無 # 構造一個Selector對象來提取數據 selector = Selector(text=browser.page_source) # 匹配整個頁面的每個商戶信息塊 items = selector.css(.shop-list.J_shop-list.shop-all-list ul li) for item in items: # 構造一個可迭代的存放商戶信息的字典 yield { # 通過xpaht獲取店名 shop: item.xpath(.//div[@class="tit"]/a/@title).extract_first(), # 通過css選擇器獲取地址 location: item.css(.addr::text).extract_first(), # 通過xpaht獲取商圈區域、商戶等級、評價數、人均消費水平 region: item.xpath(.//div[@class="tag-addr"]//a[2]//span/text()).extract_first(), level: item.xpath(//div[@class="comment"]//span/@title).extract_first(), comment: .join(item.xpath(.//a[@class="review-num"]//text()).extract()).strip().replace(
, ), consume: .join(item.xpath(.//a[@class="mean-price"]//text()).extract()).replace(
, ).replace( , ), } def main(): # 進入首頁 browser.get(URL) # 找到搜索輸入框 input = wait.until(EC.presence_of_element_located((By.ID, J-search-input))) # 以防萬一,先清除輸入框內容 input.clear() # 輸入關鍵字 input.send_keys(KEYWORD) # 回車搜索 input.send_keys(Keys.ENTER) # 切換至當前窗口選項 browser.switch_to_window(browser.window_handles[1]) # 開始依次按頁爬取 for page in range(1, MAX_PAGE+1): index_page(page)if __name__ == __main__: main()

推薦閱讀:

Selenium2+python自動化23
Selenium學習(5)滑鼠事件
Python 爬蟲練習:使用selenium+chrome爬取球探網比賽數據(ajax非同步載入)
Selenium學習(1)工具安裝

TAG:Selenium | Python | 大眾點評 |