selenium實例:自動刷青馬網課實現登陸 python實現自動登陸 利用pytesseract自動識別驗證碼並登錄

準備工作

首先得先安裝好python,IDE,selenium,Firefox瀏覽器
這裏可以供參考
Windows下的python的安裝全步驟,分圖詳解
Windows+Firefox(Chrome)+selenium+python配置並更改源(加快下載速度,不然很慢)
安裝相關的庫
pip install 相關庫的名稱即可
一般來說,需要檢查time,pytesseract,PIL等庫是否被正確安裝
如果出現報錯,安裝上相應的庫即可
推薦使用anconda進行
不用也可,測試環境在安裝好selenium的anconda下進行
注意,原本的anconda並沒有包括selenium庫,需要自行安裝
另外,我們還需要Tesseract-OCR這個軟件,用於ocr識別相關驗證碼
關於這個軟件的信息請自行百度
總的來說,爲了運行這個實例,你需要:
1.一臺裝有Windows的電腦和網絡
2.python3及其IDE(如pycharm,vscode等),最好是anconda
3.相關的python庫,如PIL,selenium等
4.運行ocr所需要的軟件Tesseract-OCR
5.Firefox瀏覽器及其對應webdriver

相關功能的實現

import pytest
import time
import json
import pytesseract
import re
import requests
import pyautogui

from time import sleep
from PIL import Image,ImageEnhance,ImageOps
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.common.action_chains import ActionChains
from selenium.webdriver.support import expected_conditions
from selenium.webdriver.support.wait import WebDriverWait
from selenium.webdriver.common.keys import Keys
from selenium.webdriver.common.desired_capabilities import DesiredCapabilities
from selenium.webdriver import FirefoxOptions
from selenium.webdriver.firefox.firefox_binary import FirefoxBinary

class Class:
    #該函數功能是初始化
    def __init__(self,un,pw,cbe,cen):
        opts = FirefoxOptions()
        # opts.add_argument("--headless")
        option_profile = webdriver.FirefoxProfile()
        option_profile.set_preference("plugin.state.flash",2)
        option_profile.set_preference("security.insecure_field_warning.contextual.enabled",False)
        #上面的部分是對瀏覽器的設置,使flash能自動播放
        self.driver = webdriver.Firefox(firefox_profile=option_profile,options=opts)
        self.driver.get('http://hnqmgc.17el.cn/')
        self.driver.set_window_size(1920,1080)
        #創建一個瀏覽器對象並打開網站,設置窗口尺寸爲1920*1080
        self.un=un
        self.pw=pw
        self.cbe=cbe
        self.cen=cen
        #接收傳入的un用戶名,pw密碼,cbe課程開始刷的id,cen課程結束刷的id
        print('初始化瀏覽器成功')

    #該函數功能是處理驗證碼
    def processing_pictures(self):
        sleep(1)
        self.driver.find_element(By.ID, "code").click()
        sleep(1)
        #找到驗證碼,點一下刷新驗證碼。因爲這個函數在一個循環體,一次可能不能登錄成功。
        self.driver.save_screenshot('pictures.png')
        #保存網頁截圖
        left=1365
        top=319
        right=1365+48
        bottom=319+18
        #上面的是驗證碼的座標
        imge=Image.open("pictures.png").crop((left, top, right, bottom))
        #imge.show() 作用是運行時檢查錯誤用的,把處理後的圖像輸出
        img = imge.convert("L")
        #圖片轉灰度,由於這個驗證碼太腦殘,不需要進行插值等特殊處理
        pixdata = img.load()
        w, h = img.size
        threshold = 160
        # img.show()
        for y in range(h):
            for x in range(w):
                if pixdata[x, y] < threshold:
                    pixdata[x, y] = 255
                else:
                    pixdata[x, y] = 0
        #取反色
        #img.show()
        pytesseract.pytesseract.tesseract_cmd = r"C:\Program Files\Tesseract-OCR\tesseract.exe"
        #這裏應該是你的ocr程序的安裝地址
        result = pytesseract.image_to_string(img)
        #將圖片轉換爲字符串
        resultj = re.sub(u"([^\u4e00-\u9fa5\u0030-\u0039\u0041-\u005a\u0061-\u007a])", "", result)
        #正則表達式,除去特殊字符
        result_four = resultj[0:4]
        print('驗證碼是'+str(result_four))
        return result_four
    
    #該函數功能是登錄
    def login(self):
        print('正在登錄中,請稍後')
        n=0
        #下面這是一個循環,因爲驗證碼可能不能一次正確,需要不斷嘗試
        while True:
            n+=1
            print('第%d次登錄中'%n)
            #下面這兩個sleep表示暫停1秒,因爲網頁需要加載,這樣更保險
            sleep(1)
            self.driver.refresh()
            #刷新頁面,因爲上一次循環登錄過,刷新重來
            sleep(1)
            self.driver.execute_script("window.scrollTo(0,document.body.scrollHeight)")
            #該js腳本作用是將滾動條滑至頂部
            self.driver.find_element(By.ID, "login_btn").click()
            self.driver.find_element(By.ID, "UserName").send_keys(self.un)
            self.driver.find_element(By.ID, "Password").send_keys(self.pw)
            #輸入用戶名以及密碼
            code=self.processing_pictures()
            self.driver.find_element(By.ID, "codein").send_keys(code)
            self.driver.find_element(By.ID, "sub").click()
            try:
                alert=self.driver.switch_to_alert()
                alert.accept()
            except:
                break
            #如果沒有彈出警告窗,也就是登錄成功,循環體結束,如果彈出,則accept關閉彈窗
            '''
            其實這個被註釋的腳本也可以實現檢查是否正常登錄
            sleep(1)
            self.driver.refresh()
            sleep(1)
            html = self.driver.page_source
            if html.find('個人中心') == -1:
                break
            '''
            print('第%d次登錄失敗,正在重試'%n)
        self.driver.execute_script("window.scrollTo(0,document.body.scrollHeight)")
        #作用見上面
        print('登錄成功,一共嘗試了%d次'%n)
        self.attend_class()

    #該函數功能是上網課
    def attend_class(self):
        print('開始刷課')
        for course in range(int(self.cbe),int(self.cen)+1):
            url='http://hnqmgc.17el.cn/ymzs/zxzr/484770_qmzx.shtml?kcid='+str(course)
            self.driver.get(url)
            # 進入相關課程播放頁面
            #sleep(30) 如果播放插件被阻塞,應該預留一點時間再重新打開它
            # coursename=self.driver.find_element_by_id("courseName").text()
            print('當前正在刷id爲{0}的課程:'.format(course))
            #下面的部分填坑
            sleep(5)


if __name__ == '__main__':
    print('****************歡迎使用青馬網課刷課系統v1.0!*****************')
    print('*             Author:STL_CC  2020.03.18  v1.0               *')
    print('*            Blog:https://blog.csdn.net/STL_CC              *')
    print('*************************************************************')
    print('請輸入相關信息:')
    username=input('Username:')
    password=input('Password:')
    cb=input('開始課程id:')
    ce=input('結束課程id:')
    print('開始刷課!')
    a = Class(username,password,cb,ce)
    a.login()

後話

1.以上程序僅實現了登陸功能,具體的刷課進程可見Python刷青馬,但是他這個實現方法只是模擬鼠標點擊,需要圖形化界面,應用場景十分有限。
2.聽說JavaScript能控制flash播放器的運行,而且selenium可以使用自定義js腳本,然而筆者沒有學過,而且已經開發了快三天,還要上課,吃不消,待有時間學完js後可能會在此填坑,如果哪位大佬懂js,可以一起繼續開發
3.課程id就是每個視頻最前面那個東東,你也可以觀察視頻鏈接
4.由於自動化測試工具的特殊性,可能要針對自己的電腦運行環境進行一些特殊的處理,這個程序我也鼓搗了很久才調好環境,如果由大佬需要技術支持,可以私信筆者。
5.這裏是開發的套件包,Firefox 55以上不支持flash自動運行,這是可以支持的版本,請用此套件開發
鏈接:https://pan.baidu.com/s/1XXHxkd5KXs5rRFyS19yt6A
提取碼:q3pp
emmmm 附件裏的python程序缺少了幾個庫,以上面的爲準

最近更新:筆者已經對js控制flash控件進行了測試,得要這個控件的屬性對外開放才行,所以目前來看只有兩種解決的方法,一個是使用autoit或者pyautogui等進行模擬鼠標點擊,另一種是我猜的,可以抓包欺騙服務器

與其花這幾天時間做這個工程,其實還不如老老實實刷,但是,通過這三天來的不斷測試,筆者掌握python複雜編程的能力有了很大提高。也瞭解了網頁的基本結構和selenium工具,以後應對簡單的工程,籤個到啥的還是很容易上手了的
也希望這個項目的某些方面能給讀者以啓發

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