国产一级a片免费看高清,亚洲熟女中文字幕在线视频,黄三级高清在线播放,免费黄色视频在线看

打開APP
userphoto
未登錄

開通VIP,暢享免費(fèi)電子書等14項(xiàng)超值服

開通VIP
滑動(dòng)驗(yàn)證碼破解:Python Selenium 2.0 應(yīng)用
本文經(jīng)作者授權(quán)發(fā)布。
本文是作者參加某驗(yàn)證碼攻防大賽后的記錄,大賽中攻擊部分用到了網(wǎng)頁自動(dòng)化測(cè)試工具Selenium。本文記錄的就是相關(guān)的方法。
文 | 楊林@Tencent
滑動(dòng)驗(yàn)證碼是新型驗(yàn)證碼的一種,區(qū)別于傳統(tǒng)的字符型驗(yàn)證碼,新型驗(yàn)證碼主要通過用戶行為來區(qū)分人和機(jī)器。
selenium 被廣泛應(yīng)用于網(wǎng)頁自動(dòng)化測(cè)試以及網(wǎng)頁爬蟲中,本次比賽我采用了 selenium 操作網(wǎng)頁元素的方式來自動(dòng)執(zhí)行滑動(dòng)驗(yàn)證碼的拖拽。 selenium 在 python 下的詳細(xì)使用方法參見 selenium python 使用文檔。
一、selenium 的配置
1)安裝
selenium 支持 python2.7 以及 python3.5 等主流 python 版本,其安裝較為簡單,有網(wǎng)的環(huán)境下,使用 pip 命令即可自動(dòng)安裝。
pip install selenium
無網(wǎng)的環(huán)境下,下載 selenium 安裝包,然后通過 python 命令也可方便安裝。
python setup.py install
2) webdriver
selenium 安裝完成后,我們需要下載所選瀏覽器的 webdriver,本文以 ChromeDriver為例,為了后面在代碼中更加方便的加載相應(yīng) webdriver,可將 webdriver 的路徑添加至系統(tǒng) PATH 變量中。
注:selenium 通過 webdriver 調(diào)用瀏覽器接口的方式支持多種瀏覽器,如:ChromeDriver,FirefoxDriver,InternetExplorerDriver,SafariDriver 等真實(shí)瀏覽器,以及:htmlunit、PhantomJS 兩個(gè)無界面瀏覽器。大致區(qū)別如下:
driver類型優(yōu)點(diǎn)缺點(diǎn)應(yīng)用
真實(shí)瀏覽器真實(shí)模擬用戶行為效率、穩(wěn)定性低兼容性測(cè)試
HtmlUnit速度快js引擎不是主流瀏覽器支持的包含少量js的頁面測(cè)試
PhantomJS支持js、速度中等、模擬行為接近真實(shí)不能模擬不同/特定瀏覽器的行為非GUI的功能性測(cè)試
selenium 選用各瀏覽器時(shí),只修改加載 webdriver 的語句即可,具體的業(yè)務(wù)邏輯代碼和網(wǎng)頁元素操作代碼不需要做任何改變。
二、selenium 在 python 下的使用
1) import
通過以下語句在 python 中引用 selenium
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
2)瀏覽器啟動(dòng)測(cè)試
啟動(dòng)瀏覽器并打開網(wǎng)址進(jìn)行測(cè)試,注意如果前面沒有將 webdriver 路徑添加至系統(tǒng) PATH 變量下,引用時(shí)需要鍵入 webdriver 的完整路徑。通過 ChromeOptions 可設(shè)置瀏覽器的初始位置和大小。
options = webdriver.ChromeOptions();
options.add_argument('--window-position=0,0');  #chrome 啟動(dòng)初始位置
options.add_argument('--window-size=1080,800');  #chrome 啟動(dòng)初始大小
driver=webdriver.Chrome(chrome_options=options)
driver.get('http://game.captcha.qq.com/hslj/html/hslj/') #比賽主頁面
此時(shí)看到 Chrome 打開了比賽的 index 頁面。
3)網(wǎng)頁元素操作
selenium-webdriver 提供了通過網(wǎng)頁元素 id、class、name、css、tagName 等方式獲取網(wǎng)頁元素的方法。用戶可根據(jù)網(wǎng)頁源碼的不同情況進(jìn)行選擇,以下代碼為自動(dòng)在比賽主頁輸入 rtx、qq 并點(diǎn)擊登錄、開始比賽的例子。
def input_by_id(self, text=u'', element_id=''):
input_el = self.driver.find_element_by_id(element_id) #通過 id 查找網(wǎng)頁元素
input_el.clear()
input_el.send_keys(text) #輸入字符串
time.sleep(0.5)
def click_by_id(self, element_id=''):
search_el = self.driver.find_element_by_id(element_id)
search_el.click() #鼠標(biāo)左鍵單擊
time.sleep(0.5)
def click_by_class(self, element_class=''):
search_el = self.driver.find_element_by_class_name(element_class) #通過 class 查找網(wǎng)頁元素
search_el.click() #鼠標(biāo)左鍵單擊
time.sleep(0.5)
self.input_by_id('wadeyang','user-input')
self.input_by_id('914645774', 'qq-input')
self.click_by_id('login-btn')
self.click_by_class('hslj-game-btn')
三、破解
搭建好 python-selenium-webdriver 環(huán)境,并了解簡單使用方法后,下面介紹一下滑動(dòng)驗(yàn)證碼的破解思路。
1)圖片獲取
為了計(jì)算滑動(dòng)驗(yàn)證碼的拖拽位置,我們首先需要獲取原始圖片和缺口圖片,通過對(duì)網(wǎng)頁 html 的分析,我們通過以下代碼獲取兩張圖片。
self.driver.switch_to.frame(self.driver.find_element_by_tag_name('iframe'))
#轉(zhuǎn)換 webdriver 的工作環(huán)境至子 iframe,通過 tag_name 查找網(wǎng)頁元素
img1ele = self.driver.find_element_by_id('totalBlock') #獲取原始 img 網(wǎng)頁元素
fatherdiv = self.driver.find_element_by_class_name('oripic')#獲取缺口 img 的 div
img2ele = fatherdiv.find_element_by_tag_name('img');#獲取缺口 img 網(wǎng)頁元素
src1 = img1ele.get_attribute('src');#得到原始 img 路徑
src2 = img2ele.get_attribute('src');#得到缺口 img 路徑
self.driver.switch_to.default_content()#轉(zhuǎn)換 webdriver 工作環(huán)境至默認(rèn)
urlopen = urllib.request #urllib 模塊,可通過 pip 安裝,import urllib 引用
fp = urlopen.urlopen(src1) #打開原始 img 路徑
data1 = fp.read() #讀取數(shù)據(jù)
fp.close()
file = open('d://1.jpg', 'w b') #將原始 img 保存為 d://1.jpg
file.write(data1)
file.close()
fp = urlopen.urlopen(src2) #打開缺口 img 路徑
data2 = fp.read()
fp.close()
file = open('d://2.jpg', 'w b') #將缺口 img 保存為 d://2.jpg
file.write(data2)
file.close()
2)缺口位置計(jì)算
在獲得原始圖片和缺口圖片后,接下來需要計(jì)算缺口的水平位置,也就是需要拖拽的距離。我們首先獲取兩張圖像素的差值。
img1 = Image.open('d://1.jpg'); #from PIL import Image 引用
img2 = Image.open('d://2.jpg');
img3 = ImageChops.difference (img1, img2); #from PIL import ImageChops 引用
再從左到右按列的方式遍歷 img3 的像素,當(dāng)遇像素值連續(xù)不為 0 數(shù)量超過 70 時(shí)停止,此時(shí)的 x 坐標(biāo)即為滑塊應(yīng)拖動(dòng)的距離。
3)拖拽軌跡采集
為了模擬正常用戶的拖拽軌跡,我們首先需要采集正常用戶拖拽驗(yàn)證碼時(shí)的鼠標(biāo)操作及運(yùn)動(dòng)軌跡。這里我利用了 GhostMouse Free 工具,并通過簡單的 C#編程解析其保存文件的方式來將正常用戶的拖拽軌跡保存成為不同的文件。c#代碼如下:
using (StreamReader sr = new StreamReader('e:\data.rms'))
{
String line;
// Read and display lines from the file until the end of
// the file is reached.
bool open = false;
int filestartindex = 1;
FileStream fs = null;
StreamWriter sw = null;
int lastX = 0, lastY = 0;
String temp = null;
Queue X = new Queue();
Queue Y = new Queue();
Queue D = new Queue();
while ((line = sr.ReadLine()) != null){
if (line.IndexOf('LMouse up') != -1 && open){
open = false;
if (X.Sum() > 0){
if (File.Exists('e:\dividemousedata\'   filestartindex   '.txt'))
File.Delete('e:\dividemousedata\'   filestartindex   '.txt');
fs = new FileStream('e:\dividemousedata\'   filestartindex   '.txt', FileMode.OpenOrCreate, FileAccess.ReadWrite); //可以指定盤符,也可以指定任意文件名,還可以為 word 等文件
filestartindex  = 1;
sw = new StreamWriter(fs); // 創(chuàng)建寫入流
sw.WriteLine(X.Sum().ToString());
while (X.Count > 0){
string x = X.Dequeue().ToString();
string y = Y.Dequeue().ToString();
string d = D.Dequeue().ToString();
sw.WriteLine(x   ' '   y   ' '   d);
}
sw.Close();
fs.Close();
}
X.Clear();
Y.Clear();
D.Clear();
}
if (line.IndexOf('LMouse down') != -1){
open = true;
temp = line.Split('(')[1];
temp = temp.Split(')')[0];
lastX = int.Parse(temp.Split(',')[0]);
lastY = int.Parse(temp.Split(',')[1]);
line = sr.ReadLine();
temp = line.Split(' ')[1];
temp = temp.Split('}')[0];
float delay = float.Parse(temp);
X.Enqueue(0); Y.Enqueue(0); D.Enqueue(delay);
continue;
}
if (open){
temp = line.Split('(')[1];
temp = temp.Split(')')[0];
int posX = int.Parse(temp.Split(',')[0]);
int posY = int.Parse(temp.Split(',')[1]);
line = sr.ReadLine();
temp = line.Split(' ')[1];
temp = temp.Split('}')[0];
float delay = float.Parse(temp);
X.Enqueue(posX - lastX); Y.Enqueue(posY - lastY); D.Enqueue(delay);
lastX = posX;
lastY = posY;
}
}
}
GhostMouse Free 工具記錄的文件,及最后生成的拖拽軌跡文件(第一行為拖拽的總長度;第一列為 x 位移,第二列為 y 位移,第三列為停頓時(shí)間):
4)拖拽軌跡還原
有了正常用戶的拖拽軌跡文件和滑塊需要拖動(dòng)的距離,我們即可對(duì)兩者進(jìn)行匹配,并對(duì)軌跡進(jìn)行還原。這里有一個(gè) trick,因?yàn)橥献Ь嚯x為 0 至 230,所以采集足夠多的軌跡文件,我們就可以不用對(duì)拖拽軌跡進(jìn)行任何縮放,對(duì)其進(jìn)行 100%的還原。
self.driver.switch_to.frame(self.driver.find_element_by_tag_name('iframe'))
dragger = self.driver.find_element_by_id(element_class)
action = ActionChains(self.driver)
action.click_and_hold(dragger).perform(); #鼠標(biāo)左鍵按下不放
action.reset_actions()
for index in range(len(x)):
action.move_by_offset(x[index], y[index]).perform(); #移動(dòng)一個(gè)位移
action.reset_actions()
time.sleep(d[index]); #等待停頓時(shí)間
action.release().perform(); #鼠標(biāo)左鍵松開
action.reset_actions()
self.driver.switch_to.default_content()
四、最后
以上以滑動(dòng)驗(yàn)證碼破解為例介紹了 selenium2.0 在 python 下的應(yīng)用。使用瀏覽器操作模擬的方式進(jìn)行滑動(dòng)驗(yàn)證碼破解與破解 js 然后直接發(fā)送請(qǐng)求的方式進(jìn)行破解相比較,主要的缺點(diǎn)是請(qǐng)求頻率太慢,優(yōu)點(diǎn)是通過簡單修改即可適應(yīng)不同平臺(tái)的滑動(dòng)驗(yàn)證碼。
題圖:pexels,CC0 授權(quán)。
本站僅提供存儲(chǔ)服務(wù),所有內(nèi)容均由用戶發(fā)布,如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請(qǐng)點(diǎn)擊舉報(bào)。
打開APP,閱讀全文并永久保存 查看更多類似文章
猜你喜歡
類似文章
selenium webdriver(python篇)(十一)
python+selenium+chrome實(shí)現(xiàn)自動(dòng)登錄百度
【python selenium的web自動(dòng)化】- PageObject模式解析及案例
Python實(shí)現(xiàn)對(duì)百度云的文件上傳
Selenium2+python自動(dòng)化27
聊聊 PC 端自動(dòng)化最佳方案: WinAppDriver
更多類似文章 >>
生活服務(wù)
分享 收藏 導(dǎo)長圖 關(guān)注 下載文章
綁定賬號(hào)成功
后續(xù)可登錄賬號(hào)暢享VIP特權(quán)!
如果VIP功能使用有故障,
可點(diǎn)擊這里聯(lián)系客服!

聯(lián)系客服