• Python爬虫如何绕过网站的验证码?
  • 发布于 2个月前
  • 364 热度
    0 评论
  • 李白羽
  • 20 粉丝 43 篇博客
  •   

在做自动化测试或者爬虫的时候,总会遇到验证码。我每次都得自己去手动输入抓取的图片验证码。现在的验证码大多分为几类:1、计算验证码 2、滑块验证码 3、识图验证码

用python识别验证码通常是这几个步骤:

1、灰度处理
2、二值化
3、去除边框(如果有的话)
4、降噪
5、切割字符或者倾斜度矫正
6、训练字体库
7、识别
首先当然是需要安装pytesseract库还有图像处理的PILLOW库了。
pip install pytesseract
pip install PILLOW
pytesseract库只是一个基础的文字识别库。
Pillow是Python里的图像处理库(PIL:Python Image Library),提供了了广泛的文件格式支持,强大的图像处理能力,主要包括图像储存、图像显示、格式转换以及基本的图像处理操作等。

PIL最重要的类是 Image class, 你可以通过多种方法创建这个类的实例;你可以从文件加载图像,或者处理其他图像, 或者从 scratch 创建。

1.首先需要导入需要的图像库:
  import Image
2.读取一张图片:
  im=Image.open('/home/Picture/test.jpg')
3.显示一张图片:
 im.show()
4.保存图片:
 im.save("save.gif","GIF")      #保存图像为gif格式
5.创建新图片:
 Image.new(mode, size)  
 Image.new(mode, size, color)  

 栗子:newImg = Image.new("RGBA",(640,480),(0,255,0))
            newImg.save("newImg.png","PNG")

6.两张图片相加:
 Image.blend(img1, img2, alpha)    # 这里alpha表示img1和img2的比例参数
7.点操作:
 im.point(function) #,这个function接受一个参数,且对图片中的每一个点执行这个函数
 比如:out = im.point(lambda i : i*1.5)#对每个点进行50%的加强
8.查看图像信息:
 im.format, im.size, im.mode
9.图片裁剪:
box = (100,100,500,500)  #设置要裁剪的区域 
region = im.crop(box)     #此时,region是一个新的图像对象。
10.图像黏贴(合并)
im.paste(region, box)#粘贴box大小的region到原先的图片对象中。
11.通道分离:
r,g,b = im.split()#分割成三个通道  ,此时r,g,b分别为三个图像对象。
12.通道合并:
im = Image.merge("RGB", (b, g, r))#将b,r两个通道进行翻转。
13.改变图像的大小:
out = img.resize((128, 128))#resize成128*128像素大小
14.旋转图像:
out = img.rotate(45) #逆时针旋转45度  
有更方便的:
region = region.transpose(Image.ROTATE_180)
15.图像转换:
out = im.transpose(Image.FLIP_LEFT_RIGHT)#左右对换。
out= im.transpose(Image.FLIP_TOP_BOTTOM)#上下对换
16.图像类型转换:
im=im.convert("RGBA")
17.获取某个像素位置的值:
im.getpixel((4,4))
18.写某个像素位置的值:

img.putpixel((4,4),(255,0,0))


举个例子, 假如我们有如下一个验证码:
from PIL import Image
from pytesseract import *
import PIL.ImageOps
def initTable(threshold=140):
    table = []
    for i in range(256):
        if i < threshold:
            table.append(0)
        else:
            table.append(1)
    return table

 im = Image.open('/Users/anderson/Downloads/1.png')
#图片的处理过程
im = im.convert('L')
binaryImage = im.point(initTable(), '1')
im1 = binaryImage.convert('L')
im2 = PIL.ImageOps.invert(im1)
im3 = im2.convert('1')
im4 = im3.convert('L')
#将图片中字符裁剪保留
box = (30,10,90,28)
region = im4.crop(box)
#将图片字符放大
out = region.resize((120,38))
asd = pytesseract.image_to_string(out)
print (asd)
print (out.show())

但是,抛出异常:
FileNotFoundError: [Errno 2] No such file or directory: ‘tesseract’
解决方案:
安装tesseract:
sudo apt install tesseract

运行结果:

完全识别了。

PIL的ImageDraw提供了一系列绘图方法,让我们可以直接绘图。比如要生成字母验证码图片:
from PIL import Image, ImageDraw, ImageFont, ImageFilter
import random
# 随机字母:
def rndChar():
    return chr(random.randint(65, 90))
# 随机颜色1:
def rndColor():
    return (random.randint(64, 255), random.randint(64, 255), random.randint(64, 255))
# 随机颜色2:
def rndColor2():
    return (random.randint(32, 127), random.randint(32, 127), random.randint(32, 127))
# 240 x 60:
width = 60 * 4
height = 60
image = Image.new('RGB', (width, height), (255, 255, 255))
# 创建Font对象:
font = ImageFont.truetype('Arial.ttf', 36)
# 创建Draw对象:
draw = ImageDraw.Draw(image)
# 填充每个像素:
for x in range(width):
    for y in range(height):
        draw.point((x, y), fill=rndColor())
# 输出文字:
for t in range(4):
    draw.text((60 * t + 10, 10), rndChar(), font=font, fill=rndColor2())
# 模糊:
image = image.filter(ImageFilter.BLUR)
image.save('code.jpg', 'jpeg')
效果如下:

现在就是对于规规矩矩的验证码,识别起来容易。但是实际中,有很多很变态的验证码,肉眼都无法识别,歪歪扭扭,还有很多干扰,识别起来就比较困难,有些还有中文字符,中文词语,这个还在 研究中。

用户评论