python web flask 图片验证码.短信验证码

登录.注册模块

注册

不同的功能会创建不同的蓝图模块,注册这块我们创建的是passport模块,当然都是在module目录里创建如图:
在这里插入图片描述
蓝图创建好了记得在app中注册
在这里插入图片描述

目录分析

在这里插入图片描述

第三方平台(云通讯)的使用

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

第三方随机生成验证码

在这里插入图片描述

图片验证码

注册好后我们先分析后台发送图片验证码的步骤

在这里插入图片描述

后端

import re
import random
import datetime
from info import sr, db
from . import passport_blue
from info import constants
from info.models import User
from info.response_code import RET
from flask import request, abort, jsonify, current_app, make_response,session
from info.utils.captcha.captcha import captcha
from info.libs.yuntongxun.sms import CCP


@passport_blue.route("/imageCodeId", methods=["get"])
def passpost():
    """
    发送图片验证码
    1.接收参数(imageCodeId)
    2.校验参数是否为空
    3.使用第三方辅助文件 生成图片验证码
    4.将验证码保存到redis
    5.返回图片验证码
    :return: 
    """
    # 1.
    # 接收参数(imageCodeId)
    imageCodeId = request.args.get("imageCodeId")

    # 2.
    # 校验参数是否为空
    if not imageCodeId:
        abort(403)
    # 3.
    # 生成图片验证码
    img_name, img_captcha, img = captcha.generate_captcha()

    # 4.
    # 将验证码保存到redis,并设置有效时长
    sr.set("ImgCode:" + imageCodeId, img_captcha)
    print(img_captcha)
    # 5.
    # 返回图片验证码
    res_img = make_response(img)
    res_img.headers["Content-Type"] = "img/jpg"
    return res_img

前端js

生成uuid:
function generateUUID() {
    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;
}

在这里插入图片描述
代码:

var imageCodeId = ""

// TODO 生成一个图片验证码的编号,并设置页面中图片验证码img标签的src属性
function generateImageCode() {
    imageCodeId=generateUUID()
    var url= "/passport/imageCodeId?imageCodeId="+imageCodeId 
    $(".get_pic_code").attr("src",url)
}

注意

在这里插入图片描述

短信验证码

发送短信验证码js

在这里插入图片描述
js源码:

function sendSMSCode() {
    // 校验参数,保证输入框有数据填写
    $(".get_code").removeAttr("onclick");
    var mobile = $("#register_mobile").val();
    if (!mobile) {
        $("#register-mobile-err").html("请填写正确的手机号!");
        $("#register-mobile-err").show();
        $(".get_code").attr("onclick", "sendSMSCode();");
        return;
    }
    var imageCode = $("#imagecode").val();
    if (!imageCode) {
        $("#image-code-err").html("请填写验证码!");
        $("#image-code-err").show();
        $(".get_code").attr("onclick", "sendSMSCode();");
        return;
    }

    var params = {
        'mobile':mobile,
        'image_code':imageCode,
        'image_code_id':imageCodeId
    };

    // TODO 发送短信验证码
    $.ajax({
        url:'/passport/sms_code',   // 请求地址
        type:'post',                // 请求方法
        data:JSON.stringify(params),// 请求参数
        contentType:'application/json',// 数据类型
        success:function (response) {  // 回调函数
            if (response.errno == '0') {
                // 发送短信验证码成功
                alert(response.errmsg);
            } else {
                alert(response.errmsg);
            }
        }
    });
}

接口

在这里插入图片描述

后端

步骤:

	1.获得参数(image_code', mobile, image_code_id, )图片验证码,手机号, 密钥
    2.校验参数
        2.1 所有参数不能为空
        2.2 手机号是否正确
        2.3 图片验证码是否正确
    3.使用 random 生成随机短信验证码
    4.将验证码保存到redis数据库
    5.使用第三方平台发送短信
    6.返回结果
@passport_blue.route("/sms_code", methods=["get", "POST"])
def sms_code():
    """
    1.获得参数(image_code', mobile, image_code_id, )图片验证码,手机号, 密钥
    
    2.校验参数
        2.1 所有参数不能为空
        2.2 手机号是否正确
        2.3 校验图片验证码是否正确
    3.使用 random 生成随机短信验证码
    4.将验证码保存到redis数据库
    5.使用第三方平台发送短信
    6.返回结果
    :return: 
    """
    # 1.
    # 获得参数(image_code', mobile, image_code_id, )图片验证码,手机号, 密钥
    imageCode = request.json.get("image_code")
    mobile = request.json.get("mobile")
    image_code_id = request.json.get("image_code_id")

    # 2.1
    # 校验参数不能为空
    if not all([imageCode, mobile, image_code_id]):
        return jsonify(errno=RET.NODATA, errmsg="参数缺少")

        # 2.2 校验手机号是否正确
    if not re.findall("^(13[0-9]|14[01456879]|15[0-35-9]|16[2567]|17[0-8]|18[0-9]|19[0-35-9])[0-9]{8}$", mobile):
        return jsonify(errno=RET.DATAERR, errmsg="参数错误")

    # 2.3
    # 校验图片验证码是否正确
    server_img_code = sr.get("ImgCode:" + image_code_id)

    if not server_img_code.strip().lower() == imageCode.strip().lower():
        return jsonify(errno=RET.DATAERR, errmsg="参数错误")


    # 3.
    # 使用 random 生成随机短信验证码
    random_sms = "%04d" % random.randint(0, 9999)
    print(random_sms)

    # 4.
    # 将验证码保存到redis数据库
    try:
        sr.set("SMS_Code:" + mobile, random_sms,ex=constants.IMAGE_CODE_REDIS_EXPIRES)
    except Exception as e:
        current_app.logger.error(e)
        return jsonify(errno=RET.DBERR, errmsg="数据库保存错误")

    # 5.
    # 发送短信\
 
    ccp = CCP().send_template_sms(mobile, [random_sms, constants.IMAGE_CODE_REDIS_EXPIRES / 60], 1)
    if ccp != 0:
        return jsonify(errno=RET.DATAERR, errmsg="参数错误")
    # 6.
    # 返回结果
    return jsonify(errno=RET.OK, errmsg="发送短信成功")

注册

注册按钮 js:

在这里插入图片描述
代码:

// TODO 注册按钮点击
    $(".register_form_con").submit(function (e) {
        // 阻止默认提交操作
        e.preventDefault()

		// 取到用户输入的内容
        var mobile = $("#register_mobile").val()
        var smscode = $("#smscode").val()
        var password = $("#register_password").val()

		if (!mobile) {
            $("#register-mobile-err").show();
            return;
        }
        if (!smscode) {
            $("#register-sms-code-err").show();
            return;
        }
        if (!password) {
            $("#register-password-err").html("请填写密码!");
            $("#register-password-err").show();
            return;
        }

		if (password.length < 6) {
            $("#register-password-err").html("密码长度不能少于6位");
            $("#register-password-err").show();
            return;
        }


        // 发起注册请求
        var params = {
            'mobile':mobile,
            'smscode':smscode,
            'password':password
        };

        $.ajax({
            url:'/passport/register', // 请求地址
            type:'post', // 请求方法
            data:JSON.stringify(params), // 请求参数
            contentType:'application/json',
            headers:{'X-CSRFToken':getCookie('csrf_token')}, // 在请求头中带上csrf_token
            success:function (response) {
                if (response.errno == '0') {
                    // 注册成功
                    location.reload();
                } else {
                    alert(response.errmsg);
                }
            }
        });

    })
})

接口

在这里插入图片描述

后端

步骤

	1 接收参数 ( mobile,smscode,password)
    2 校验参数
        2.1 参数是否为空
        2.2 手机号是否正确
        2.3 redis存储的短信验证码是为空
        2.4 短信验证码是否一样  
    3 写入用户表
    4 保持状态
    5.返回结果
@passport_blue.route("/register", methods=["POST"])
def register():
    """
    1 接收参数 ( mobile,smscode,password)
    2 校验参数
        2.1 参数是否为空
        2.2 手机号是否正确
        2.3 redis存储的短信验证码是为空
        2.4 短信验证码是否一样
        
    3 写入用户表
    4 保持状态
    5.返回结果
    :return: 
    """


    # 1
    # 接收参数(mobile, smscode, password)
    mobile = request.json.get("mobile")
    smscode = request.json.get("smscode")
    password = request.json.get("password")

    # 2
    # 校验参数
    # 2.1
    # 参数是否为空
    if not all([mobile, smscode, password]):
            return jsonify(errno=RET.PARAMERR, errmsg="参数缺少")

    # 2.2
    # 手机号是否正确
    if not re.findall("^(13[0-9]|14[01456879]|15[0-35-9]|16[2567]|17[0-8]|18[0-9]|19[0-35-9])[0-9]{8}$", mobile):
            return jsonify(errno=RET.DATAERR, errmsg="参数错误")
    # 2.3
    # redis存储的短信验证码是为空
    try:
        server_smscode=sr.get("SMS_Code:" + mobile)
    except Exception as e:
        current_app.logger.error(e)
        return jsonify(errno=RET.DBERR, errmsg="验证码已失效")
    # 2.4
    # 短信验证码是否一样
    if not server_smscode == smscode.strip():
        return jsonify(errno=RET.DATAERR,errmsg="短信验证码不一致")

    # 3
    # 写入用户表
    user=User()
    user.nick_name=mobile
    user.mobile=mobile
    user.last_login=datetime.datetime.now()
    user.password=password

    try:
           db.session.add(user)
           db.session.commit()
    except Exception as e:
        current_app.logger.error(e)
        db.session.rollback()
        return jsonify(errno=RET.DBERR, errmsg="注册失败")

    # 4
    # 保持状态
    session["user_id"]=user.id
    session["user_mobile"] = user.mobile
    session["user_nick_name"] = user.nick_name
    # 5.
    # 返回结果
    return jsonify(errno=RET.OK,errmsg="注册成功")

登录

注册后我们都有保持登录在session写值
在首页渲染的时候获得session判断是否有值,没值右上角出现登录/注册,有值展示个人信息
在这里插入图片描述
后端:
在index渲染之前做处理所以在index模块
步骤:

@index_blue.route("/")
def index():
    """
    首页
    1.右上登录处理
        1.1 获得session
        1.2 用session在数据库中查找
        1.3 返回结果
    :return: 
    """

    # 获得session
    user_id=session.get("user_id")


    # 用session在数据库中查找
    user=None
    try:
        user = User.query.filter_by(id=user_id).first()
    except Exception as e:
        current_app.logger.error(e)
        abort(404)


    content={
        "user":user
    }
    # 返回结果
    return render_template("news/index.html",content=content)

前端逻辑展示:
在这里插入图片描述

退出登录:

将session的值删掉在重新渲染首页

@passport_blue.route("/logout", methods=["get", "POST"])
def logout():
    """
    退出登录
    1.删除session
    2.返回结果
    :return: 
    """
    # 1.
    # 删除session
    session.pop("user_id",None)
    session.pop("user_mobile", None)
    session.pop("user_nick_name", None)

    # 2.
    # 返回结果
    return jsonify(errno=RET.OK,errmsg="退出成功")

在这里插入图片描述

退出js

function logout() {
    // $.ajax({
    //     url:'/passport/logout',
    //     type:'get'
    // });

    $.get('/passport/logout', function (response) {
        if (response.errno == '0') {
            // 退出登录成功
            location.reload();
        } else {
            alert(response.errmsg);
        }
    })
}
  • 0
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值