Python3爬蟲知識(問題)彙總(一)

Python:python3

以下是本人在爬蟲項目中遇到並積累的問題與知識點:

一、獲取國內髙匿代理IP網站的免費IP代理,並驗證哪些IP爲可用代理,最後將可用代理輸出。

       首先需要爬取到代理IP的協議、ip地址、端口,本人採用了兩種形式的獲取:一個是常見的bs4庫的BeautifulSoup與requests庫,另一個是模擬瀏覽器selenium庫。

1、PhantomJS

       這裏如果用selenium庫需要安裝PhantomJS,當然還有其他的瀏覽器。如下圖,其中android與blackberry是移動端的瀏覽器,先不管。移動端的瀏覽器雖然支持JavaScript,但與PC段瀏覽器是兩回事。剩下的chrome、Edge、Firefox、IE、Opera、Phantomjs和Safari比較常用。

       PhantomJS是一個機遇WebKit的服務器端JavaScript API。它全面支持Web而不需瀏覽器支持,其快速、原生支持各種Web標準:DOM處理、CSS選擇器、JSON、Canvas和SVG。PhantomJS可以用於頁面自動化、網絡監測、網頁截屏及無界面測試等。

       無界面意味着開銷小、速度快。有人測試過,使用selenium調用以上的瀏覽器,速度最快的爲PhantomJS、Chrome和IE(remote調用HtmlUnit最快,但對JavaScript不太友好)。唯一缺點就是沒有GUI(界面)。

說明:

       2018年3月PhantomJS的作者ariya在PhantomJS的GitHub頁面說道可能會停止更新維護。在未來的通知之前,PhantomJS 2.1.1將會是已知最後的穩定版本。暫停開發的話,可以用別的工具。

       例如本地調試基於Selenium+PhantomJS的動態爬蟲程序順利結束後,着手部署到服務器上,京東雲安裝環境,最後跑的時候報了這麼個錯誤:

UserWarning: Selenium support for PhantomJS has been deprecated, please use headless versions of Chrome or Firefox instead

       新版本的Selenium不再支持PhantomJS了,請使用Chrome或Firefox的無頭版本來替代。

2、Firefox

       CSDN上的孔天逸從Mozilla上提供了Selenium+Headless Firefox在Python上實現的方法:

from selenium.webdriver import Firefox
from selenium.webdriver.common.by import By
from selenium.webdriver.common.keys import Keys
from selenium.webdriver.firefox.options import Options
from selenium.webdriver.support import expected_conditions as expected
from selenium.webdriver.support.wait import WebDriverWait
if __name__ == "__main__":
options = Options()
options.add_argument('-headless') # 無頭參數
driver = Firefox(executable_path='geckodriver', firefox_options=options) # 配了環境變量第一個參數就可以省了,不然傳絕對路徑
wait = WebDriverWait(driver, timeout=10)
driver.get('http://www.google.com')
wait.until(expected.visibility_of_element_located((By.NAME, 'q'))).send_keys('headless firefox' + Keys.ENTER)
wait.until(expected.visibility_of_element_located((By.CSS_SELECTOR, '#ires a'))).click()
print(driver.page_source)
driver.quit()

       作者也說了,本地要有Firefox;本地要有geckodriver,最好再配置一下環境變量;別每下載一個網頁實例化一個webdriver(Firefox or Chrome)然後就close()掉,實例化webdriver的時間也是時間~推薦將下載器做成單例類或將webdirver做類變量。

3、Chrome

       下載網址:https://chromedriver.storage.googleapis.com/index.html

ChromeDriver 76.0.3809.12 (2019-06-07)---------Supports Chrome version 76
ChromeDriver 75.0.3770.8 (2019-04-29)---------Supports Chrome version 75
ChromeDriver v74.0.3729.6 (2019-03-14)--------Supports Chrome v74
ChromeDriver v2.46 (2019-02-01)----------Supports Chrome v71-73
--------以下爲2018年兼容版本對照表-------

ChromeDriver v2.45 (2018-12-10)----------Supports Chrome v70-72
ChromeDriver v2.44 (2018-11-19)----------Supports Chrome v69-71
ChromeDriver v2.43 (2018-10-16)----------Supports Chrome v69-71
ChromeDriver v2.42 (2018-09-13)----------Supports Chrome v68-70
ChromeDriver v2.41 (2018-07-27)----------Supports Chrome v67-69
ChromeDriver v2.40 (2018-06-07)----------Supports Chrome v66-68
ChromeDriver v2.39 (2018-05-30)----------Supports Chrome v66-68
ChromeDriver v2.38 (2018-04-17)----------Supports Chrome v65-67
ChromeDriver v2.37 (2018-03-16)----------Supports Chrome v64-66
ChromeDriver v2.36 (2018-03-02)----------Supports Chrome v63-65
ChromeDriver v2.35 (2018-01-10)----------Supports Chrome v62-64

 

       將解壓後的chromedriver.exe放到chrome瀏覽器或python的安裝目錄下。

       對於Chrome,博客園上的zhuxiaoxi提供瞭解決方案(需要安裝chromedriver):

from selenium import webdriver
from selenium.webdriver.chrome.options import Options
chrome_options = Options()
chrome_options.add_argument('--headless')
chrome_options.add_argument('--disable-gpu')
driver = webdriver.Chrome(chrome_options=chrome_options)
driver.get("https://cnblogs.com/")

二、驗證代理IP用常規requests.get(url,proxies={'https':proxy})。

        requests命令會先判斷proxies參數裏面傳入的key(http/https),看它與目標url協議是否一致,比如如果url是http,proxies裏面也是傳入的http,或者同是https,那麼此時requests就會認爲代理有效,就會通過代理來訪問這個url。如果url是http,但是key是https,或者url是https,但是key是http,那麼requests就會認爲兩者不匹配,就會直接去訪問目標地址而不走代理。
一個特殊情況就是,如果url是http的,proxies的key也是http的,但是key的value我傳入https代理,此時由於requests發現協議也是一致的,所以也會通過代理來請求,此時由於公司的https代理也能處理這個http請求,所以代理成功。

三、Python3中urllib就是urllib,urllib2是urllib.request。

import urllib.request #  urllib2是urllib.request
if __name__ == "__main__":
    #訪問網址
    url = 'http://www.shixi.com/search/?page=1'
    #這是代理IP
    ip = ip_list[1]
    #設置代理ip訪問方式,http和https
    proxy = {'https':ip}
    #創建ProxyHandler
    proxy_support = urllib.request.ProxyHandler(proxy)
    #創建Opener
    opener = urllib.request.build_opener(proxy_support)
    #添加User Angent
    opener.addheaders = [('User-Agent','Mozilla/5.0')]
    #安裝OPener
    urllib.request.install_opener(opener)
    #使用自己安裝好的Opener
    response = urllib.request.urlopen(url)
    #讀取相應信息並解碼
    html = response.read().decode("gbk")
    #打印信息
    print(html)


px = urllib.request.ProxyHandler({'https':ip})
# 用build_opener()來構建一個opener對象
opener = urllib.request.build_opener(px)
headers = {
    "User-Agent": "Mozilla/5.0"}
res = urllib.request.Request(url, headers=headers)
response = opener.open(res, timeout=3)
print(response)
re = response.read().decode('gbk')
print(re)

四、python動態爬取(翻頁網址不變問題)

       目前遇見的有兩種情況:

1.拉勾網:https://www.lagou.com/gongsi/3-0-0

       查看網頁的變換特點,具體可以參考:https://blog.csdn.net/c350577169/article/details/80410133

2.騰訊視頻vip片庫:https://film.qq.com/film_all_list/allfilm.html?type=tv

       這個在From Data中沒有明顯的特點,但是可以採用模擬瀏覽器點擊的方式。

def next_page(url,page_number):
    try:
        # 等待確認按鈕加載完成
        browser.get(url)
        confirm_btn = wait.until(EC.element_to_be_clickable((By.CSS_SELECTOR, '#filmPager > a.page_next.js_pager_arrow_next')))
        # 確認點擊翻頁
        confirm_btn.click()
        # 確認已翻到下一頁
        wait.until(EC.text_to_be_present_in_element((By.CSS_SELECTOR, '#filmPager > a.page_num.current.js_page_index'),str(page_number))) 
    except TimeoutException:
        # 若發生異常,重新調用自己
        next_page(page_number)

五、使用模擬瀏覽器時報錯

1.當使用Chrome瀏覽器時,需要界面滾動到顯示確認按鈕的地方,如果不在當前視圖範圍內的元素的操作,否則會報錯。

       當使用Firefox webdriver來測試某個頁面的時候,如果選取了某個頁面元素來對其進行操作,但是這個元素不在當前瀏覽器顯示的視圖範圍內,Firefox webdriver的做法是自動的將視圖調整到該元素顯示的區域,然後對這個元素進行操作。也就是說driver自己完成了頁面的scroll down or up的操作。

       但是在Chrome webdriver中,如果待操作元素不在視圖顯示範圍內,則會拋出Element is not clickable at point異常。或是如果設置了WebDriverWait並且它正常工作的話會拋出Timeout異常。因此,在使用Chrome wbedriver的時候,需要滾動頁面才能顯示在視圖中的元素,利用代碼使頁面滾動至元素顯示的範圍,然後再對該元素進行操作。使頁面滾動的方法是:

driver.execute_script("window.scrollBy(0,200)","")  #向下滾動200px
driver.execute_script("window.scrollBy(0,document.body.scrollHeight)","")  #向下滾動到頁面底部 

 2.Chrome 的驅動不匹配,則也會報錯,需要下載最新的放到原有目錄下。

        這個問題在上面也提到過,只需要檢查電腦的谷歌版本是什麼,然後再去Google官網下載對應版本即可。

        在谷歌瀏覽器的右上角的設置中的幫助查看關於“Google Chrome”,這裏的是71。

        在該網址:https://chromedriver.storage.googleapis.com/index.html中選擇合適的版本。

        打開可以看到不同的插件,選擇合適的插件下載。

       將解壓後的chromedriver.exe放到chrome瀏覽器或python的安裝目錄下。

 

項目進行中,持續更新······

文章未經博主同意,禁止轉載!

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章