Flask 生成動態二維碼登錄

看了很多篇生成動態二維碼的帖子,但是,都是片段,前言後語都沒有.主要研究的這篇
然後自身也不夠理解flask基本語言結構,所以頭大,

皇天不負有心人,後來看了一些教程,再加上同事小姐姐指導,終究是給跑明白了

當然這個練習只是一個小模塊,頂多算是一個網頁登錄過程的一個小小的組成部分,所以僅作爲熟悉練習使用

先看下文件結構

  • joinsuccess.html 用來登陸成功顯示的,內容自定
  • login.html 是存儲Flask Form的
  • forms.py 是定義了一個類,但後來我把裏邊的類直接copy進views.py裏了,所以這個文件可以忽略
  • validate_picture.py 這個是生成動態驗證碼的函數
  • view.py 是這個登錄網頁的主結構

在這裏插入圖片描述

validate_picture.py


from PIL import Image, ImageFont, ImageDraw, ImageFilter
import random
import os

current_path = os.path.split(os.path.realpath(__file__))[0]

def validate_picture():   #驗證碼代碼函數
    total = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ012345789'
    # 圖片大小130 x 50
    width = 130
    heighth = 50
    # 先生成一個新圖片對象
    im = Image.new('RGB', (width, heighth), 'white')
    # 設置字體
    font = ImageFont.truetype(current_path + '/simkai.ttf', 37)
    # 創建draw對象
    draw = ImageDraw.Draw(im)
    str = ''
    # 輸出每一個文字
    for item in range(5):
        text = random.choice(total)
        str += text
        draw.text((5 + random.randint(4, 7) + 20 * item, 5 + random.randint(3, 7)), text=text, fill='red', font=font)

    # 劃幾根干擾線
    for num in range(8):
        x1 = random.randint(0, width / 2)
        y1 = random.randint(0, heighth / 2)
        x2 = random.randint(0, width)
        y2 = random.randint(heighth / 2, heighth)
        draw.line(((x1, y1), (x2, y2)), fill='yellow', width=1)

    # 模糊下,加個帥帥的濾鏡~
    im = im.filter(ImageFilter.FIND_EDGES)

    return im, str

# ----------------------------

if __name__ == '__main__':
    img,str=validate_picture()
    print(str)
    img.show()



view.py (這裏邊標註的都沒刪,可以自行刪除)

from flask import Flask, render_template, make_response, session
# from utils.code import Code
from validate_picture import validate_picture
from flask import Flask, render_template, request, flash
# 導入wtf擴展的表單類
from flask_wtf import FlaskForm
# 導入自定義表單需要的字段
from wtforms import SubmitField, StringField, PasswordField, BooleanField
# 導入wtf擴展提供的表單驗證器
from wtforms.validators import DataRequired, EqualTo
from io import BytesIO
# from PIL import Image, ImageFont, ImageDraw, ImageFilter
# import random
import os

auth = Flask(__name__)
# auth.secrete_key='sumer'
auth.config["SECRET_KEY"] = "12345678sumer"


class LoginForm(FlaskForm):
    email = StringField('電子郵箱', validators=[DataRequired()])
    password = PasswordField('密碼', validators=[DataRequired()])
    verify_code = StringField('驗證碼', validators=[DataRequired()])
    remember_me = BooleanField('記住我的用戶')
    submit = SubmitField('登錄')


current_path = os.path.split(os.path.realpath(__file__))[0]




@auth.route('/code')
def get_code():
    image, code_str = validate_picture()
    # 將驗證碼圖片以二進制形式寫入在內存中, 防止將圖片都放在文件夾中,佔用大量磁盤
    buf = BytesIO()
    image.save(buf, 'jpeg')
    buf_str = buf.getvalue()
    # 把二進制作爲response發回前端,並設置首部字段
    response = make_response(buf_str)
    response.headers['Content-Type'] = 'image/gif'
    # 將驗證碼字符串儲存在session中
    session['image'] = code_str
    return response


@auth.route('/login', methods=['GET', 'POST'])
def login():
    form = LoginForm()
    # 1. 判斷請求參數

    if request.method == 'POST':
        # 2.獲取請求參數
        email = request.form.get('email')
        password = request.form.get('password')
        verify_code = request.form.get('verify_code')

        # 3.驗證參數,WTF可以一句話實現所有校驗
        if form.validate_on_submit():
            # return 'success '
            if str.lower(session.get('image')) != str.lower(verify_code):
                print(session.get('image'))

                flash('驗證碼錯誤')
            if str.lower(session.get('image')) == str.lower(verify_code):
                return render_template('joinsuccess.html')
            # user = User.query.filter_by(email=form.email.data).first()
            # # 驗證用戶的登錄密碼
            # if user is not None and user.verify_password(form.password.data):
            #     login_user(user, form.remember_me.data)
            #     flash('驗證通過,登錄成功')
            #     return redirect(request.args.get('next') or
            #                     url_for('main.index'))
            else:
                flash('用戶名或者密碼不正確')

    return render_template('login.html', form=form)

@auth.route('/')
def hello():
    return '''\n\n\n
    <h3>隱藏掃一掃助力!<br></h1><img src="https://github.com/rovesoul/PyTorch-Chinese-Guide/blob/master/%E5%B1%8F%E5%B9%95%E5%BF%AB%E7%85%A7%202019-10-20%20%E4%B8%8B%E5%8D%8810.50.07.png?raw=true">
    <br><br><a href="http://127.0.0.1:5000/login">--點擊進行驗證碼登錄--</a><br><br>
    查看登錄頁面,需要在上方地址欄補加入 login <br>再回車就能進入了.<br>因爲在views的login調用頁面函數裏,是/login'''




if __name__ == "__main__":
    auth.run(debug=True)
    p=get_code()
    print(type(response))

login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
{#     <title>二維碼測試</title> #}

</head>
<body>

{#   extends "base.html" #}
{#   import "bootstrap/wtf.html" as wtf #}

    {% block page_content %}
        <div class="page-header">
            <h1>Login</h1>
        </div>




        <form method="post">
              {{ form.csrf_token() }}
              {{ form.email.label }}<br>{{ form.email }}<br>
              {{ form.password.label }}<br>{{ form.password }}<br>
              {{ form.verify_code.label }}<br>{{ form.verify_code }}<br>
              {{ form.remember_me.label }}<br>
              {{ form.submit }}<br>

        </form>
        <div class="col-md-4">
            <!--點擊圖片重新獲取驗證碼-->
            <img  src="/code " onclick="this.src='/code?'+ Math.random()">
        </div>

    {% endblock %}

</body>
</html>

joinsuccess.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>登陸成功</title>
</head>
<body>
<h1>success </h1>
</body>
</html>

最終登錄頁面如此:

登錄處

登錄成功
祝學習,玩的愉快~

發佈了44 篇原創文章 · 獲贊 5 · 訪問量 1962
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章