天天看點

selenium自動化案例(一)B站專欄爬蟲寫在前面案例分析代碼實作

文章目錄

  • 寫在前面
  • 案例分析
  • 代碼實作

寫在前面

前幾天學習了selenium自動化以及CSS、Xpath元素定位,想着找個網站練練手,不用登入的B站就是個不錯的選擇,下面以B站的校園學習專欄為例進行視訊标題及外鍊資訊的爬取。

測試環境

Windows 10 x64

Python 3.6.8

VS code

案例分析

  • 第一步當然是檢視關鍵資訊的定位,這裡直接右鍵複制Xpath就OK,不過也需要思考Xpath的對應變化,比如翻頁後哪些值變了而哪些值不變,找到翻頁後的規律就能順利寫代碼了。
  • 接下來需要考慮翻頁的實作,我一開始考慮的是從url入手,但是采用selenium的話會很浪費資源,于是就選擇頁面内翻頁,這裡就要想想具體怎麼實作了。下面代碼中的

    page_plus_1()

    函數是我的直接思路,就是直接用Xpath定位,但是在抓取到第五頁時候其标簽就發生變化了(采用标簽序号定位穩定性較差),于是我直接定位網頁中的頁面跳轉輸入框,每次頁碼增1,就可以了。
  • 最後,是循環的處理,這裡我用了while循環并設定跳出條件,内部嵌套了每一頁的條目循環,感覺還可以提高代碼運作效率,不過作為小白的我還是先打好基礎吧。

不得不說selenium庫的封裝還是很便攜的,除了Xpath要費點事,剩下的都可以直接調用現成的方法。下面是代碼的具體實作。

代碼實作

# 用于設定強制等待
from time import sleep
# 浏覽器自動化引擎
from selenium import webdriver

def web_auto_gain_item(page_num, item_num):
    # 每一頁顯示20個條目
    # 定位待抓取文字
    elems_title = driver.find_elements_by_xpath(
       '//*[@id="videolist_box"]/div[2]/ul/li[%d]/div/div[2]/a'%(item_num)
        )
    for elem in elems_title:
        # 抓取内容為:視訊标題及外部連結(需要讀取屬性值)
        content = elem.text + ': ' + elem.get_attribute("href") + '\n'
        # 存儲内容至文本檔案,設定編碼以存儲文本字元串
        with open('bilibili_tech_list.txt', 'a', encoding='utf-8') as file:
            file.write(content)
        print(content)
    if item_num==20:
        print("第%d頁抓取完成\n"%(page_num)+'-'*30)
        sleep(1)

def page_plus_1(page_num):
    # 定位翻頁按鈕,進行翻頁操作
    # 第一頁的翻頁位于li[7], 之後的翻頁位于li[8]
    # (但是由于使用數字定位标簽,導緻其魯棒性不高,是以下面考慮第二種辦法)
    if page_num==1:
        # 點選翻頁
        driver.find_element_by_xpath(
            '//*[@id="videolist_box"]/div[2]/div[2]/ul/li[7]/button'
            ).click()
    else:
        driver.find_element_by_xpath(
            '//*[@id="videolist_box"]/div[2]/div[2]/ul/li[8]/button'
            ).click()

def page_plus_2(page_num):
    # 定位元素:網頁翻頁的
    driver.find_element_by_xpath(
        '//*[@id="videolist_box"]/div[2]/div[2]/div/input'
        ).send_keys('%d\n'%(page_num+1))


if __name__ == '__main__':

    # 待抓取的連結
    url = '''https://www.bilibili.com/v/technology/campus/#
    /all/stow/0/1/2020-08-07,2020-08-14'''
    # 執行個體化自動化引擎
    driver = webdriver.Edge(r"C:\msedgedriver.exe")
    driver.get(url)
    # 設定隐性等待
    driver.implicitly_wait(15)
    # 開始抓取
    while True:
        # 強制等待1s,便于讀取頁碼資訊
        sleep(1)
        page_num = eval(driver.current_url.split("/")[-2])
        print("開始抓取第%d頁"%(page_num))

        # 循環提取item資訊
        for item_num in range(1,21):
            web_auto_gain_item(page_num, item_num)

        # 抓取一頁完成後進行翻頁
        page_plus_2(page_num)

        # 設定循環跳出的條件,這裡以抓取5頁,20*5=100條視訊資訊為例
        if page_num == 5:
            print("抓取完畢,關閉浏覽器,謝謝使用!")
            # 關閉浏覽器,釋放記憶體
            driver.close()
            break