天天看點

爬取動态網頁遇到的問題及解決項目場景:問題描述原因分析:解決方案:

項目場景:

本文是描述本人在使用爬蟲進行動态網頁資料(在網頁中想要爬取的資料不在該網頁的源代碼中)的爬取時,遇到了問題和爬取動态網頁的解決。

問題描述

我在學校學習時,使用的是selenium進行爬取網頁的資料,在爬取一般的網頁時能夠正常的爬取,在我做另外的項目的時候爬取的資料使用selenium爬取居然連網頁都進不去,顯示的視窗直接是一片空白,使用了在網上selenium設定反反爬都不行,下面的一部分是使用browsermobproxy,進行爬取時遇到的問題(我電腦上有原來安裝的java18的版本與最新的browsermobproxy版本沖突了,需要改成java8的版本)。修改成功後也是連網頁都進不去。最後經過幾天的查詢,找到了另外的方法進行解決,使用from seleniumwire import webdriver 方法是對selenium庫進行了擴充的。

原因分析:

我電腦上原本的java的jdk版本是18.幾,幾乎是最新的,但是browsermobproxy在start這一步的時候就已經報錯,這個問題時因為兩個版本沖突了,browsermobproxy最新的已經是browsermob-proxy-2.1.4版本了,對應的jdk版本居然是jdk8
爬取動态網頁遇到的問題及解決項目場景:問題描述原因分析:解決方案:

解決方案:

在電腦上重新安裝一個jdk8環境,有兩個版本在電腦上也會不沖突,我就沒有删除原來的那個版本(jdk8是一個長期版本,很多人使用的),安裝兩個環境以後,後面安裝的那個版本會覆寫之前的那個版本。安裝好jdk8版本後需要重新開機電腦,

jdk8安裝包和教程連結:jdk安裝教程

需要說明的是在安裝jdk環境時,似乎不能更改安裝路徑,否則會報錯(我本來是想安裝到D盤的,結果他會安裝失敗),

重新開機電腦就能成功運作

server.start()
      

在這一部分,是為将使用browsermobproxy爬取不了網頁的人引入到這裡,下面使用的方法直接幫我解決了網頁的爬取。

我使用的環境:

python 3.7

selenium-wire  5.1.0

window 11 

時間:

2023/2/8

安裝
      
pip install selenium-wire
           

 導入庫

from seleniumwire import webdriver
           

使用庫之前先将selenium将Google Chrome的路徑進行修改

點選桌面的谷歌浏覽器,

點選屬性,進入下圖界面

爬取動态網頁遇到的問題及解決項目場景:問題描述原因分析:解決方案:

将浏覽的路徑最後面加上

--remote-debugging-port=9222

在按确定進行修改(這是一種設定爬蟲的方法)

下面這個連接配接裡有很多的selenium反反爬的設定:反反爬相關設定

from seleniumwire import webdriver
import time


wd = webdriver.Chrome()
wd.get(current_url)    # 這裡的網頁就不拿出來了
time.sleep(3)   # 加載網頁資訊

res = wd.requests   # 得到網頁的資訊
for request in res:
    if request.response:   # 得到目标網頁的響應
        if request.path == "/uniontrain/trainapi/TrainPCCommon/SearchTrainRemainderTickets":  # 因為我爬取的網頁資料沒在響應的資料中隻能找到相關的子連結進行爬取資料,我爬取的網頁path具有唯一性,都找到我想要的所有資料 
            train_url=request.url     # 檢視想要的資料是否在request.response中可以debug到request.response,檢視裡面的資訊。


# 這裡的request.url就是我想爬取的資料的網頁了
           

# 檢視想要的資料是否在request.response中可以debug到request.response,檢視裡面的資訊。

子網頁中資料格式為jQuery22222 ()的資料(下面是進入子網頁檢視到的内容)

爬取動态網頁遇到的問題及解決項目場景:問題描述原因分析:解決方案:

 将資料得到後是字元串的形式,我們需要将字元串轉化成json檔案,直接使用

json.loads函數是會報錯的,需要先将'jQuery183026019933464466005_1675845834371('和最後面的一個)進行删除      
data.split("(", 1)[1].rsplit(")", 1)[0]
           

下面是我将子網頁的資料進行轉換,

from selenium.webdriver.chrome.options import Options
from seleniumwire import webdriver
from selenium.webdriver.support.wait import WebDriverWait   # 顯示等待
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions as EC
from bs4 import BeautifulSoup   # 解析網頁資料
import json

options = Options()

wd = webdriver.Chrome()   
wd.get(train_url)   # 子網頁
WebDriverWait(wd, 30, 0.5).until(EC.presence_of_element_located((By.TAG_NAME, 'pre')))  # 顯示等待,當

res = wd.page_source   
soup = BeautifulSoup(res, "lxml")    
for pre in soup.find_all("pre"):
    data = pre.text  # 擷取得到的資料是str類型的
    mydict = json.loads(data.split("(", 1)[1].rsplit(")", 1)[0])  # 将字元串轉換成字典
    result=mydict['data']["trains"]    # 一個網頁中的所有資訊   # 可以通過debug檢視想要的資料
           

以上内容就是我在爬取做項目内容時遇到的問題的解決。