第一关:
url: http://www.heibanke.com/lesson/crawler_ex00/
打开网页是这样的
自己试几次就可以发现规律,此次的数字是下一次请求的数字,手动操作任务量还是挺大的,通关后大概是这样:
源码如下:
import os,sys
import re
import requests
reload(sys)
sys.setdefaultencoding('utf-8')
# 第一关 猜数字
# 此次的数字是下一次请求的数字
# url: http://www.heibanke.com/lesson/crawler_ex00/
def ex01():
# 匹配数字
def findNum(url):
res = requests.get(url).content
num = re.findall('数字[^\d]*(\d+)[\.<]',res)
return num
# 首先获得数字
url = "http://www.heibanke.com/lesson/crawler_ex00/"
num = findNum(url)
# 循环直至出来结果
while num:
url2 = url+num[0]
num = findNum(url2)
print u'访问网页:%s'%url2
else:
print u'第二关网页:%s'%url2
以上就是第一关。
接下来是第二关:
url: http://www.heibanke.com/lesson/crawler_ex01/
页面打开是这样的:
通过页面很直观的知道,密码是30以内,所以我就没把30放在考虑范围内,也就是说是0-29。
后来查看此次关卡传的参数,发现出来用户名和密码之外还多了一个csrfmiddlewaretoken,于是就去页面找了下,猜想是这个value,试了下,果然是
源码如下:
#-*- coding:utf-8 -*-
#author:Koelre
# 黑板课爬虫闯关
# url: http://www.heibanke.com/lesson/crawler_ex00/
import os,sys
import re
import requests
from lxml import etree
reload(sys)
sys.setdefaultencoding('utf-8')
# 获取csrf值
def getcsrf():
url = 'http://www.heibanke.com/lesson/crawler_ex01/'
res = requests.get(url,timeout=30).text
tree = etree.HTML(res)
csrf = tree.xpath('/html/body/div/div/div[2]/form/input/@value')[0]
return csrf
# 第二关 猜密码
# 密码是30以内,所以我就没把30放在考虑范围内,就是0-29
# url: http://www.heibanke.com/lesson/crawler_ex01/
def ex02():
scrf = getcsrf()
url = 'http://www.heibanke.com/lesson/crawler_ex01/'
data = {
"csrfmiddlewaretoken": str(scrf),
"username": "a",
"password": "1"
}
for x in xrange(30):
data["password"] = x
res = requests.post(url,data=data).content
if u"错误" not in res:
print u"密码:%s"%x
break
接下来是第三关:
url: http://www.heibanke.com/lesson/crawler_ex02/
页面打开是这样的:
这个首先就需要登录啦,注册登录之后打开就是这样的:
所以,第三关相对第二关就需要登录了,密码还是30以内,所以我就没把30放在考虑范围内,就是0-29
接下来是第四关:
url: http://www.heibanke.com/lesson/crawler_ex03/
页面打开是这样的:
看见这样蒙圈,于是输入试试:
发现已经不是输入密码那么简单了,所以 在这里耐心找
:
上下翻了几页也才明白,意思是说:虽然说同样需要登录,我看了好几遍才清楚它的密码逻辑,“密码的位置”最大的是100,所以,密码长度应该是100个,如果只是遍历完一遍显示的页数,数字可能会达不到100个,所以这样就需要循环几遍才能得到所有的。
接下来是第五关:
url: http://www.heibanke.com/lesson/crawler_ex04/
页面打开是这样的:
发现除了需要登录,输入密码(同样是数字 - 就从0开始),还多了一个验证码,经查看,验证码就是一种图片,我的方案就是每次把那个图片下载下来在本地识别就OK了。
源码如下:
#-*- coding:utf-8 -*-
# 黑板课爬虫闯关
# url: http://www.heibanke.com/lesson/crawler_ex00/
import os,sys
import re
import random
import requests
from lxml import etree
import pytesseract
from PIL import Image,ImageEnhance
reload(sys)
sys.setdefaultencoding('utf-8')
# 登录
# 3,4,5都需要登录
# url: http://www.heibanke.com/accounts/login
def login():
website1 = 'http://www.heibanke.com/accounts/login'
se = requests.Session()
se.get(website1)
token1 = se.cookies['csrftoken']# 保存csrftoken
# 登录参数
dataWebsite1 = {
'username': 'Koelre',
'password': 'lixue961314',
'csrfmiddlewaretoken': token1
}
res = se.post(website1, data=dataWebsite1)#登录
print res.status_code
return se
# 第三关 猜密码
# url: http://www.heibanke.com/lesson/crawler_ex02/
def ex03():
website2 = 'http://www.heibanke.com/lesson/crawler_ex02/'
s = login()# 登录
for x in xrange(30):
# 以下步骤原理和上面一样
token2 = s.cookies['csrftoken']
dataWebsite2 = {
'username': 'a',
'password': x,
'csrfmiddlewaretoken': token2
}
result = s.post(website2, data=dataWebsite2).content
if u"错误" not in result:
print u"3--密码:%s"%x
break
# 第四关 猜密码
# url: http://www.heibanke.com/lesson/crawler_ex03/
def guesspass(se,password):
website2 = 'http://www.heibanke.com/lesson/crawler_ex03/'
dataweb2 = {
"csrfmiddlewaretoken": "JUwPvezXy54mqH5MrklkBSiecn1ZZnqv",
"username": "a",
"password": password
}
req = se.post(website2,data=dataweb2).content
return req
# 收集密码的值
passes = ['' for x in range(101)]
def ex04():
global passes
se = login()# 登录
# for i in range(1,14):
passwebsite = 'http://www.heibanke.com/lesson/crawler_ex03/pw_list/?page=1'#+str(i)
# 密码
res = se.get(passwebsite).content
etr = etree.HTML(res)
# 第一个是标题
trs = etr.xpath('/html/body/div/div/div/table/tr')[1:]
for tr in trs:
pa1 = tr.xpath('td[1]/text()')[0].strip()#密码位置
pa1 = int(re.findall('\d+',pa1)[0])
pas = tr.xpath('td[2]/text()')[0].strip()#密码的值
passes[pa1] = pas
password = ''.join(passes)#把密码拼接字符串
if len(password)==100:
# 猜密码
result = guesspass(se,password)
# 判断密码是否猜对
if u"错误" not in result:
print u"4--密码:%s"%password
else:
ex04()
# 第五关
# url: http://www.heibanke.com/lesson/crawler_ex04/
def VerificationCode(imgurl):
# 保存验证码
imgs = requests.get(imgurl).content
with open('1.jpg','wb') as f:
f.write(imgs)
image = Image.open('1.jpg')
imgry = image.convert('L')#图像加强,二值化
sharpness = ImageEnhance.Contrast(imgry)#对比度增强
sharp_img = sharpness.enhance(2.0)
sharp_img.save('1.jpg')
text = pytesseract.image_to_string(image)
return text
def ex05(a=1,passd=1):
website = 'http://www.heibanke.com/lesson/crawler_ex04/'
se = login()# 登录
res1 = se.get(website)
# print res1.status_code
etr = etree.HTML(res1.content)
token2 = etr.xpath('/html/body/div/div/div[2]/form/input/@value')[0].strip()
imgsrc = etr.xpath('/html/body/div/div/div[2]/form/div[3]/img/@src')[0].strip()
#验证码链接
imgurl = 'http://www.heibanke.com'+str(imgsrc)
#图片code
capcodes = etr.xpath('//*[@id="id_captcha_0"]/@value')[0]
# 保存验证码图片且识别验证码
text = VerificationCode(imgurl)
# print capcodes,text,passd
web2data = {
"csrfmiddlewaretoken":token2,
"username":"a",
"password":passd,
"captcha_0":capcodes,
"captcha_1":text
}
# 提交信息 - 开始猜测
# 尝试每个数字多猜几次,验证码有时候会识别错误
res2 = se.post(website,data=web2data,timeout=30).content
if u"验证码输入错误" not in res2:
if u"密码错误" not in res2:
with open('pass.txt','ab') as f:
f.write(u"密码是:%s"%passd)
else:
ex05(a,passd+1)
else:
# 多输入几次验证码,预防验证码错误
if a<=3:
ex05(a+1,passd)
else:
a=1
ex05(a,passd+1)
github上面也放源码了,点它就可以了 -- >> github-crawler
网友评论