django 使用PIL生成验证码
python=3.6.8
django=2.1.8
Pillow=7.0.0
redis=3.3.1
工具形式的验证码生成,并存入redis
import random
import io
import redis
from PIL import ImageDraw, ImageFont, Image
from mysite.settings import BASE_DIR
def get_random_color():
"""
定义随机的字体颜色
:return:
"""
R = random.randrange(255)
G = random.randrange(255)
B = random.randrange(255)
return (R, G, B)
# 获取验证码视图
def mycode(image_id):
# 画布
img_size = (120, 50)
# 定义图画对象
image = Image.new('RGB', img_size, 'white')
# 定义画笔对象
draw = ImageDraw.Draw(image, 'RGB')
# 定义随机字符串
source = '0123456789'
# 定义容器
code_str = ''
# 定义字体
my_font = ImageFont.truetype(font="{}\myutils\fonts\SourceCodePro-Bold.ttf".format(BASE_DIR), size=20)
for i in range(4):
# 获取随机颜色
text_color = get_random_color()
# 获取随机字符串长度下标(index)
tmp_num = random.randrange(len(source))
random_str = source[tmp_num]
code_str += random_str
# 将字符串添加到画布上
draw.text((10+30*i, 20), random_str, text_color, font=my_font)
# 建立缓存区
buf = io.BytesIO()
# 建立redis连接
conn_redis = redis.Redis(host='127.0.0.1', port=6379, db=1)
# 保存随机码到redis中
conn_redis.set(image_id, code_str, ex=300) # ex代表seconds,px代表ms
# 保存图片
image.save(buf, 'png')
return buf.getvalue()
views.py
from django.views import View
from django.http import HttpResponse
from myutils.common import mycode
class RandomImageView(View):
def get(self, request, image_id): # 生成的验证码的key值
return HttpResponse(mycode(image_id), 'image/png')
urls.py
from django.urls import path
from . import views
urlpatterns = [
path('random_image/<str:image_id>/', views.RandomImageView.as_view()), # 随机生成验证码 ]
vue中Register.vue
<template>
<div>
<form >
<ul>
<li>
<label>用户名:</label>
<input type="text" v-model="username" >
</li>
<li>
<label>密 码:</label>
<input type="password" v-model="password" >
</li>
<li>
<label>验证码:</label>
<input type="text" v-model="image_code" class="msg_input" >
<img :src="image_code_url + code_cid + '/'" id="msg_code" @click="refresh" alt="图形验证码" class="pic_code">
</li>
<li class="reg_sub">
<input type="submit" value="登 陆" name="">
</li>
</ul>
</form>
</div>
</template>
<script>
export default {
data() {
return {
username: '',
password: '',
image_code: '',
code_cid: '',
image_code_url: 'http://127.0.0.1:8000/day01/random_image/',
}
},
methods: {
// 生成uuid随机字符串
generate_uuid() {
var d = new Date().getTime();
if (window.performance && typeof window.performance.now === "function") {
d += performance.now(); //use high-precision timer if available
}
var uuid = "xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(
/[xy]/g,
function(c) {
var r = (d + Math.random() * 16) % 16 | 0;
d = Math.floor(d / 16);
return (c == "x" ? r : (r & 0x3) | 0x8).toString(16);
}
);
return uuid;
},
// 点击图片刷新验证码
refresh(){
this.code_cid = this.generate_uuid()
},
},
mounted() { // 页面加载完成以后,生成验证码
this.code_cid = this.generate_uuid()
}
}
</script>
CBV形式的验证码(简单)
from django.conf import settings
from django.views import View
from django.http import HttpResponse
import random
import io
import redis
from PIL import ImageDraw, ImageFont, Image
class MyRandomStr(View):
"""
定义验证码类,用来生成验证码
"""
# 定义随机颜色
def get_random_color(self):
R = random.randrange(255)
G = random.randrange(255)
B = random.randrange(255)
return (R, G, B)
# 获取验证码视图
def get(self, request, image_id):
# 画布
img_size = (120, 50)
# 定义图画对象
image = Image.new('RGB', img_size, 'white')
# 定义画笔对象
draw = ImageDraw.Draw(image, 'RGB')
# 定义随机字符串
source = '0123456789'
# 定义容器
code_str = ''
# 定义字体
my_font = ImageFont.truetype(font="{}\myutils\fonts\SourceCodePro-Bold.ttf".format(settings.BASE_DIR), size=15)
for i in range(4):
# 获取随机颜色
text_color = self.get_random_color()
# 获取随机字符串长度下标(index)
tmp_num = random.randrange(len(source))
random_str = source[tmp_num]
code_str += random_str
# 将字符串添加到画布上
draw.text((10+30*i, 20), random_str, text_color, font=my_font)
# 建立redis连接
conn_redis = redis.Redis(host='127.0.0.1', port=6379, db=1)
# 保存随机码到redis中
conn_redis.set(image_id, code_str, ex=5) # ex代表seconds,px代表ms
# 建立缓存区
buf = io.BytesIO()
# 保存图片
image.save(buf, 'png')
return HttpResponse(buf.getvalue(), 'image/png')
验证码(复杂)
from PIL import Image, ImageDraw, ImageFont
import redis
from verify.settings import FONTS_DIRS
import random
import os
from django.http import HttpResponse
import io
# Create your views here.
def generate_image_code(request, image_id):
# 图片验证码
'''
本地图片验证码生成函数
'''
bgcolor = (random.randrange(20, 100), random.randrange(
20, 100), random.randrange(20, 100))
width = 110
height = 40
# 创建画面对象
im = Image.new('RGB', (width, height), bgcolor)
# 创建画笔对象
draw = ImageDraw.Draw(im)
# 调用画笔的point()函数绘制噪点
for i in range(0, 100):
xy = (random.randrange(0, width), random.randrange(0, height))
fill = (random.randrange(0, 255), 255, random.randrange(0, 255))
draw.point(xy, fill=fill)
# 定义验证码的备选值
str = '1234567890QWERTYUIOPASDFGHJKLZXCVBNMqwertyuiopasdfghjklzxcvbnm'
# 随机选取4个值作为验证码
code_str = ''
for i in range(0, 4):
code_str += str[random.randrange(0, len(str))]
# 构造字体对象
fonts_files = os.path.join(
FONTS_DIRS, 'SourceCodePro-Bold.ttf')
font = ImageFont.truetype(fonts_files, 30)
# 构造字体颜色
fontcolor1 = (255, random.randrange(0, 255), random.randrange(0, 255))
fontcolor2 = (255, random.randrange(0, 255), random.randrange(0, 255))
fontcolor3 = (255, random.randrange(0, 255), random.randrange(0, 255))
fontcolor4 = (255, random.randrange(0, 255), random.randrange(0, 255))
# 绘制4个字
draw.text((5, 2), code_str[0], font=font, fill=fontcolor1)
draw.text((25, 2), code_str[1], font=font, fill=fontcolor2)
draw.text((50, 2), code_str[2], font=font, fill=fontcolor3)
draw.text((75, 2), code_str[3], font=font, fill=fontcolor4)
# 释放画笔
del draw
# 存入缓存,用于做进一步验证,并设置超时时间为10分组
print(rand_str)
# 建立redis连接
conn_redis = redis.Redis(host='127.0.0.1', port=6379, db=1)
# 保存随机码到redis中
conn_redis.set(image_id, code_str, ex=5) # ex代表seconds,px代表ms
buf = io.BytesIO()
# 将图片保存在内存中,文件类型为png
im.save(buf, 'png')
# 将内存中的图片数据返回给客户端,MIME类型为图片png!
return HttpResponse(buf.getvalue(), 'image/png')