django与小程序实现登录验证功能的示例代码


Posted in Python onFebruary 19, 2019

之前用小程序做项目,因为后台使用的java开发,一切顺利,但切换成django做RESTful API接口时,在登陆注册时一直出现问题,网上搜索,借助一个网友的回答,找到了一种可行的解决方案,现记录如下。

具体流程

  • 用户点击小程序页面上的登录授权认证
  • 通过微信自带的认证获取code
  • 调取登录接口,将code传入后台
  • 后台拿到code调用微信接口获取openid等用户信息
  • 后台将openid作为用户名,若存在则去校验用户信息,否则以此用户名创建新用户,密码随机生成
  • 将校验结果或者创建信息返回给微信小程序端
  • 根据返回的信息完成用户登录校验

django的用户权限认证

django有一套自己的完善用户模型,由于Django Auth自带的User模型字段有限,我们需要对其进行拓展(直接使用也可以)

nickname = models.CharField(verbose_name=u'昵称',max_length=50, blank=True)
user_avatar = models.ImageField(verbose_name=u'用户头像', upload_to='image/%Y/%m/%d', default=u'image/default.png', max_length=500)
user_email = models.EmailField(verbose_name=u'用户邮箱',max_length=254)
user_phone = models.BigIntegerField(verbose_name=u'手机号', null=True,blank=True)
user_birthday = models.DateField(verbose_name=u'出生日期', default = timezone.now)
user_sex = models.CharField(verbose_name=u'性别',max_length=6,choices=(('male','男'),('female','女')),default='male')
user_address = models.CharField(verbose_name=u'地址',max_length=550, blank=True,null=True)
signature = models.CharField(verbose_name=u'个性签名',max_length=550, blank=True,null=True)

用户接口序列化

from rest_framework import serializers

class UserSerializer(serializers.ModelSerializer):
class Meta:
  model = User
  fields = "__all__"

登陆接口设计

class UserLogin(APIView):
  def post(self,request):
    params = request.data
    userName = get_openid(params.get('code'))
    userInfo = params.get('userinfo')
    try:
      user = User.objects.get(username = userName)
    except Exception as e:
      user = None
    if user:
      # 更新用户信息
      user = User.objects.get(username = userName)
    else:
      #注册新用户
      user = User.objects.create_user(username=userName,password=random_str(10))  
    #手动生成JWT
    # 手动生成token验证
    jwt_payload_handler = api_settings.JWT_PAYLOAD_HANDLER
    jwt_encode_handler = api_settings.JWT_ENCODE_HANDLER
    payload = jwt_payload_handler(user)
    token = jwt_encode_handler(payload)

    ret = {'code': '00000', 'msg': None,'data':{}}
    
    ret['msg'] = '授权成功'
    ret['data'] = {
      'token': token,
      'user_id': user.id,
      'nickname': user.nickname
    }
    return JsonResponse(ret)

解析code获取openid

class OpenidUtils(object):
  def __init__(self, jscode):
    self.url = "https://api.weixin.qq.com/sns/jscode2session"
    self.appid = APPID
    self.secret = SECRET
    self.jscode = jscode  # 前端传回的动态jscode

  def get_openid(self):
    url = self.url + "?appid=" + self.appid + "&secret=" + self.secret + "&js_code=" + self.jscode + "&grant_type=authorization_code"
    r = requests.get(url)
    openid = r.json()['openid']
    return openid

小程序的登陆验证

具体登录流程可以查阅官方文档。

function getWXUserInfo() {
  const login = promisify(wx.login);
  const getUserInfo = promisify(wx.getUserInfo);

  return new Promise(function (resolve, reject) {
    _wxLogin();
    function _wxLogin() {
      login().then(function (res) {
        getUserInfo().then(function (r) {
          let userInfo = r;
          userInfo.code = res.code;
          try {
            wx.setStorageSync('userInfo', userInfo);
          } catch (e) {
            console.log(e)
          }
          if (userInfo && userInfo.code && userInfo.iv) {
            resolve(userInfo);
          }
          else {
            reject('wx login fail');
          }
        }).catch(function (error) {
          reject(error);
        });
      }).catch(function (error) {
        reject(error);
      });
    }
  });
}

//登录接口验证
getWXUserInfo().then(function (data) {
  var result = {
    code: 0,
    data: {}
  };
  var params = {
    'code':data.code,
    'userinfo':data.userInfo
  }
  wx.request({
    url: '/api/login',
    data: params,
    dataType: 'json',
    method: 'POST',
    success: function (response) {
      // 返回成功
      if (response.data && response.data.code == '00000') {
        try {
          var resData = {
            custNo: data.user_id,
            nickname: data.nickname
          };
          result.code = 0;
          result.data = resData;
          resolve(result);
        }
        catch (e) {
          console.warn(result)
          // 登录失败
          result.code = 2;
          resolve(result);
        }
      }
      else {
        // 获取 customNum 失败
        console.warn(result)
        result.code = 1;
        result.data = 'get customNum fail';
        resolve(result);
      }
    }
  })
}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
使用python实现baidu hi自动登录的代码
Feb 10 Python
跟老齐学Python之有点简约的元组
Sep 24 Python
详解Python异常处理中的Finally else的功能
Dec 29 Python
使用python为mysql实现restful接口
Jan 05 Python
Python操作MySQL数据库的三种方法总结
Jan 30 Python
使用Eclipse如何开发python脚本
Apr 11 Python
pytorch + visdom CNN处理自建图片数据集的方法
Jun 04 Python
python3 爬取图片的实例代码
Nov 06 Python
Python面向对象程序设计之类的定义与继承简单示例
Mar 18 Python
Django项目创建到启动详解(最全最详细)
Sep 07 Python
Python使用Chrome插件实现爬虫过程图解
Jun 09 Python
Python 文本滚动播放器的实现代码
Apr 25 Python
实例讲解Python3中abs()函数
Feb 19 #Python
python协程之动态添加任务的方法
Feb 19 #Python
Python同步遍历多个列表的示例
Feb 19 #Python
python读取txt文件并取其某一列数据的示例
Feb 19 #Python
详解Python3注释知识点
Feb 19 #Python
Python3解释器知识点总结
Feb 19 #Python
python 利用文件锁单例执行脚本的方法
Feb 19 #Python
You might like
PHP session文件独占锁引起阻塞问题解决方法
2015/05/12 PHP
WordPress中获取页面链接和标题的相关PHP函数用法解析
2015/12/17 PHP
JavaScript 异步调用框架 (Part 1 - 问题 & 场景)
2009/08/03 Javascript
自定义一个jquery插件[鼠标悬浮时候 出现说明label]
2011/06/27 Javascript
Js-$.extend扩展方法使方法参数更灵活
2013/01/15 Javascript
js定时器的使用(实例讲解)
2014/01/06 Javascript
JavaScript实现Fly Bird小游戏
2016/12/15 Javascript
利用 spin.js 生成等待效果(js 等待效果)
2017/06/25 Javascript
vue基于element的区间选择组件
2018/09/07 Javascript
小程序使用wxs解决wxml保留2位小数问题
2019/12/13 Javascript
微信小程序学习总结(五)常见问题实例小结
2020/06/04 Javascript
原生js拖拽功能制作滑动条实例代码
2021/02/05 Javascript
[03:57]2016完美“圣”典风云人物:rOtk专访
2016/12/09 DOTA
python3图片转换二进制存入mysql
2013/12/06 Python
Python中MySQL数据迁移到MongoDB脚本的方法
2016/04/28 Python
使用Turtle画正螺旋线的方法
2017/09/22 Python
python http接口自动化脚本详解
2018/01/02 Python
Python字符串的常见操作实例小结
2019/04/08 Python
使用CSS3制作倾斜导航条和毛玻璃效果
2017/09/12 HTML / CSS
H5 canvas中width、height和style的宽高区别详解
2018/11/02 HTML / CSS
canvas绘制太极图的实现示例
2020/04/29 HTML / CSS
英国最大的在线床超市:Bed Star
2019/01/24 全球购物
WSDL的操作类型主要有几种
2013/07/19 面试题
个人找工作自荐信格式
2013/09/21 职场文书
毕业设计计划书
2014/01/09 职场文书
入党思想汇报怎么写
2014/04/03 职场文书
环保倡议书范文
2014/05/12 职场文书
预备党员转正思想汇报
2014/09/26 职场文书
司法局群众路线教育实践活动整改措施思想汇报
2014/10/13 职场文书
鲁迅故里导游词
2015/02/05 职场文书
学生会生活部工作总结2015
2015/03/31 职场文书
失恋33天观后感
2015/06/11 职场文书
2015年政治教研组工作总结
2015/07/22 职场文书
高一语文教学反思
2016/02/16 职场文书
2019新员工心得体会
2019/06/25 职场文书
Python使用永中文档转换服务
2022/05/06 Python