天天看点

django项目开发模拟auth的做一个登录验证(一)

一、说明

在一个项目开发中涉及到前端与后台管理系统,一般我们后台管理系统使用

django

中自带的

auth

作为用户登录退出,及装饰器类的,但是前端页面就需要自己书写了
  • 1、下面列举了常用的

    auth

    模块
    from django.contrib.auth.models import User
    from django.contrib.auth import authenticate, logout, login
    from django.contrib.auth.decorators import login_required
               
    • 1、

      authenticate

      是校验用户账号与密码是否正确
    • 2、

      logout, login

      表示登录与退出的方法
    • 3、

      login_required

      登录的装饰器
    • 4、

      User

      django

      中自带的用户表

二、前端页面模拟一个

auth

的上述功能

  • 1、创建一个前端的

    app

    并在

    settings.py

    中注册
  • 2、在创建的

    app

    models.py

    中创建一个前端用户模型(需要字段自己扩展)
    from __future__ import unicode_literals
    
    from django.db import models
    import uuid
    
    # 前端用户的数据模型
    
    class FrontUserModel(models.Model):
        uid = models.UUIDField(primary_key=True,default=uuid.uuid4)
        email = models.EmailField(unique=True)
        username = models.CharField(max_length=)
        password = models.CharField(max_length=)
        is_active = models.BooleanField(default=True)
        date_joined = models.DateTimeField(auto_now_add=True)
        last_joined = models.DateTimeField(auto_now=True)
               
  • 3、映射到数据库中
  • 4、测试刚刚映射数据模型是否成功(写一个测试的视图存储数据,查看数据库密码是明文保存的)
    from django.http import HttpResponse
    from django.shortcuts import render
    from frontauth.models import FrontUserModel
    
    # 测试代码  
    
    def test(request):
        user = FrontUserModel(email='[email protected]',password='123')
        user.save()
        return HttpResponse('success')
               

三、对提交的密码加密处理(简单的使用

MD5

加密)

主要思路
  • 1、获取到用户提交的密码
  • 2、使用加密算法对提交的明文密码进行加密处理
  • 3、把加密后的密码放到需要提交的字段里面
  • 4、调用保存方法把刚加密后的密码提交到数据库中
  • 5、测试
下面具体实现以上四步加密算法后测试
  • 1、获取到用户提交的密码
    每次我们提交数据都要调用

    save()

    方法,在这个方法之前截获提交的明文秘密
    class FrontUserModel(models.Model):
        ### 此处省去建表的字段   
    
        def __init__(self,*args,**kwargs):
            if 'password' in kwargs:
                print '*'*
                print kwargs['password']
                print '*'*
               
  • 2、使用加密算法对提交的明文密码进行加密处理
    import hashlib
    class FrontUserModel(models.Model):
        ### 此处省去建表的字段   
    
        def __init__(self,*args,**kwargs):
            if 'password' in kwargs:
                # 定义一个加密的盐(随便输入的)
                salt = 'sjhahoibsaGHSAoiwhsoa'
                password = hashlib.md5(salt+kwargs['password']).hexdigest()
                print '*'*
                print password
                print '*'*
               
  • 3、把加密后的密码放到需要提交的字段里面
    import hashlib
    class FrontUserModel(models.Model):
        ### 此处省去建表的字段   
    
        def __init__(self,*args,**kwargs):
            if 'password' in kwargs:
                # 定义一个加密的盐(随便输入的)
                salt = 'sjhahoibsaGHSAoiwhsoa'
                password = hashlib.md5(salt+kwargs['password']).hexdigest()
                kwargs['password'] = password
               
  • 4、调用保存方法把刚加密后的密码提交到数据库中
    import hashlib
    class FrontUserModel(models.Model):
        ### 此处省去建表的字段   
    
        def __init__(self,*args,**kwargs):
            if 'password' in kwargs:
                # 定义一个加密的盐(随便输入的)
                salt = 'sjhahoibsaGHSAoiwhsoa'
                password = hashlib.md5(salt+kwargs['password']).hexdigest()
                kwargs['password'] = password
            # 使用父类的保存方法
            super(FrontUserModel, self).__init__(*args, **kwargs)    
               
  • 5、测试

四、用户登录校验密码(就是一个解密的过程)

主要步骤
  • 1、截获用户输入的密码,对其再一次使用上面的方式加密
  • 2、加密后的密码去与数据库里面的密码匹配
  • 3、返回

    True

    或者

    False

  • 4、测试
    # 定义一个校验密码的
    
    def check_password(self,raw_password):
        if not raw_password:
            return False
        # 定义一个加密的盐(注意这个要复制上面的)
        salt = 'sjhahoibsaGHSAoiwhsoa'
        hash_password = hashlib.md5(salt + raw_password).hexdigest()
        if self.password == hash_password:
            return True
        else:
            return False
               
    # 测试代码  
    
    def test(request):
        # user = FrontUserModel(email='[email protected]',password='123')
        # user.save()
        email = '[email protected]'
        password = '123'
        user = FrontUserModel.objects.filter(email=email).first()
        if user.check_password(password):
            return HttpResponse('success')
        else:
            return HttpResponse('fail')
               

五、修改密码的方法

  • 1、修改密码的方法
    # 定义一个修改密码的方法 
    
    def set_password(self, raw_password):
        if not raw_password:
            return None
        # 定义一个加密的盐(注意这个要复制上面的)
        salt = 'sjhahoibsaGHSAoiwhsoa'
        hash_password = hashlib.md5(salt + raw_password).hexdigest()
        self.password = hash_password
        self.save(update_fields=['password'])
               
  • 2、测试
    # 测试代码  
    
    def test(request):
        # user = FrontUserModel(email='[email protected]',password='123')
        # user.save()
        email = '[email protected]'
        password = '234'
        user = FrontUserModel.objects.filter(email=email).first()
        user.set_password('234')
        return HttpResponse('success')
               

六、整理上面代码(抽取公共部分)

  • 1、全部的盐可以提取出来,定义在一个配置文件里面
    **configs.py文件中**
    
    # 定义一个盐
    
    PASSWORD_SALT = 'sjhahoibsaGHSAoiwhsoa'
               
  • 2、加密的方法也重复多次写了
    **hashers.py文件**
    import configs
    import hashlib
    
    
    # 定义一个加密的方法
    
    def make_password(raw_password,salt=None):
        if not salt:
            salt = configs.PASSWORD_SALT
        hash_password = hashlib.md5(salt+raw_password).hexdigest()
        return hash_password
    
    
    # 定义一个解密的方法
    
    def check_password(raw_password,hash_password):
        if not raw_password:
            return False
        tmp_password = make_password(raw_password)
        if tmp_password == hash_password:
            return True
        else:
            return False
               
  • 3、使用
    # -*- coding: utf-8 -*-
    
    from __future__ import unicode_literals
    
    from django.db import models
    import uuid
    from hashers import make_password, check_password
    
    
    class FrontUserModel(models.Model):
        uid = models.UUIDField(primary_key=True, default=uuid.uuid4)
        email = models.EmailField(unique=True)
        username = models.CharField(max_length=)
        password = models.CharField(max_length=)
        is_active = models.BooleanField(default=True)
        date_joined = models.DateTimeField(auto_now_add=True)
        last_joined = models.DateTimeField(auto_now=True)
    
        def __init__(self, *args, **kwargs):
            if 'password' in kwargs:
                password = make_password(kwargs['password'])
                kwargs['password'] = password
            # 使用父类的保存方法
            super(FrontUserModel, self).__init__(*args, **kwargs)
    
        # 定义一个校验密码的
        def check_password(self, raw_password):
            return check_password(raw_password, self.password)
    
        # 定义一个修改密码的方法
        def set_password(self, raw_password):
            if not raw_password:
                return None
            hash_password = make_password(raw_password)
            self.password = hash_password
            self.save(update_fields=['password'])
               
  • 4、测试

七、使用加密模块来进行加密

可以参考我之前

tornado

处理加密的方式进行加密传送门,就不说怎么安装与使用模块了,直接上案例
  • 1、导包
    from pbkdf2 import PBKDF2
               
  • 2、书写写入,校验,修改密码的方法
    # 使用pbkdf2第三方加密模块来处理
    
    class WebUserModel(models.Model):
        uid = models.UUIDField(primary_key=True, default=uuid.uuid4)
        email = models.EmailField(unique=True)
        username = models.CharField(max_length=)
        password = models.CharField(max_length=)
        is_active = models.BooleanField(default=True)
        date_joined = models.DateTimeField(auto_now_add=True)
        last_joined = models.DateTimeField(auto_now=True)
    
        def __init__(self, *args, **kwargs):
            if 'password' in kwargs:
                # iterations表示迭代多少次
                new_password = PBKDF2.crypt(kwargs['password'], iterations=)
                kwargs['password'] = new_password
            # 使用父类的保存方法
            super(WebUserModel, self).__init__(*args, **kwargs)
    
        # 定义一个校验密码的方法
        def check_password(self, raw_password):
            if not raw_password:
                return False
            return self.password == PBKDF2.crypt(raw_password, self.password)
    
        # 定义一个修改密码的方法
        def set_password(self, raw_password):
            if not raw_password:
                return None
            new_password = PBKDF2.crypt(raw_password, iterations=)
            self.password = new_password
            self.save(update_fields=['password'])
               
  • 3、测试

八、个人建议使用

pbkdf2

模块加密方式,或者推荐使用自定义加密方式传送门