學習記錄:爬取個人微博

我的個人微博早前有大量跟好友的頁面聊天數據,隨著時間增多,發的微博近乎上萬條,可是微博本身沒有提供數據備份功能,查看了一下API文檔,從官方提供的接口取得的數據也只是有限條,無法滿足需要,因此萌發了寫個爬蟲用模擬登錄的方式將所有發過的微博抓取下來。

一 、先分析一下微博網頁版的結構和流程:

首先是登錄,需要用戶名、密碼、驗證碼,登錄成功后進入個人微博主頁,在主頁右邊有一個年份側邊欄,從這里可以按時間查看所有發過的微博,這就是我主要的抓取對象了,再進一步查看頁面結構可知,微博按年月進行數據讀取,每一個月的微博有可能為0,也有可能有好幾頁,每一頁需要將頁面滾動到底部幾次才會完全加載出來。

二、然后準備好工具:

Python 3.6
selenium 3.3.3
火狐瀏覽器驅動 geckodriver-v0.15.0-win64

三、難點與重點:

1、模擬登錄過程

新浪微博的網頁版登錄過程比起別的有一點小曲折,它需要先輸入用戶名驗證后才會顯示驗證碼,不過既然是用selenium模擬,這些都不是問題。

verifyimg = browser.find_element_by_css_selector("img[node-type='verifycode_image']")  //驗證碼圖片
num = 0
while verifyimg.get_attribute('src') == "about:blank":
    num = num + 1
    if num == 5:
        logger.info("驗證碼無法加載,請重試!")
        browser.quit()
        return
    userInput.click()  //模擬點擊用戶輸入框以觸發驗證碼顯示
    time.sleep(8)
    pwInput.click()
    time.sleep(5)

模擬登錄的重點是對驗證碼圖片進行截圖保存,用于后續人工識別輸入,這一行代碼我花了半天進行文檔查詢和編寫調試,目前是在火狐瀏覽器上調試成功,但是后面我將驅動換成phantomjs,截取下來的卻是整個頁面。

verifyimg.screenshot("verifycode.png")

2、用腳本將頁面拉到底部讀取數據

從selenium官方文檔上查到的方法,版本是3.3.3。

browser.execute_script("window.scrollTo(0, document.body.scrollHeight);")

3、判斷某個年月的微博是否有下一頁

由于為了方便抓取,設置了多個參數,于是為了判斷下一頁,各種語句調試了一天,才整出下面這段代碼:

//pages:要下載的頁面數;page:當前第幾頁;pagecount:總頁面數
if (not pages) or (not isinstance(pages[0], int)) or (pages[0] > pagecount) or (pages[0] >= pagecount - page) or (pages[0] <= 0): #不傳翻頁數或者翻頁數參數錯誤
        if page < pagecount:        
            page = page + 1
            getWeiboHtml(datenum, url, count, page)
        elif page == pagecount:
            logger.info("保存完畢!")
            return
  elif (pages[0] > 0) and (pages[0] < pagecount - page):
        if pages[0] == 1:
            logger.info("保存完畢!")
            return
        else:
            page = page + 1
            flip = pages[0]-1
            getWeiboHtml(datenum, url, count, page, flip)
    else:
        return

4、獲取到第一條微博和最新一條微博的日期

第一條微博日期是通過點擊微博主頁的時間線,獲取網址中的stat_date字段數據。
最新一條微博日期直接就從登錄后的微博主頁內容字段中解析。

5、日志系統

這次這個爬蟲項目,不光學到了selenium的使用,還學到了Python自帶的日志系統的使用,受益匪淺。
下面的函數使日志系統從文件里讀取配置。

def setup_logging(
    default_path='logconfig.json', 
    default_level=logging.INFO,
    env_key='LOG_CFG'):
    path = default_path
    value = os.getenv(env_key, None)
    if value:
        path = value
    if os.path.exists(path):
        with open(path, 'r') as f:
            config = json.load(f)
        logging.config.dictConfig(config)
    else:
        logging.basicConfig(level=default_level)

然后在程序中引入日志進行記錄:

import logging.config
logger = logging.getLogger(__name__)

6、selenium的安裝

裝selenium的時候并不順利,一開始是想用chrome瀏覽器的,但是下載了chrome的驅動后無法使用,折騰了好久最后改用了火狐。

四、進階

目前微博是以html文件的形式保存下來了,但是還需要繼續編寫解析器從html里面提取出結構化的數據,還有區別原創與轉發,對表情和圖片進行下載等,待以后有時間需要一一進行解決。
目前寫的爬蟲僅能在自己的機子上以命令行的形式運行,想要給朋友使用都不行,因此還要繼續學習Python的打包與界面化。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容