用户名登录

用户名登录后端逻辑

class LoginView(View):
    """用户名登录"""

    def get(self, request):
        """
        提供登录界面
        :param request: 请求对象
        :return: 登录界面
        """
        return render(request, 'login.html')

    def post(self, request):
        """
        实现登录逻辑
        :param request: 请求对象
        :return: 登录结果
        """
        # 接受参数
        username = request.POST.get('username')
        password = request.POST.get('password')
        remembered = request.POST.get('remembered')

        # 校验参数
        # 判断参数是否齐全
        if not all([username, password]):
            return http.HttpResponseForbidden('缺少必传参数')

        # 判断用户名是否是5-20个字符
        if not re.match(r'^[a-zA-Z0-9_-]{5,20}$', username):
            return http.HttpResponseForbidden('请输入正确的用户名或手机号')

        # 判断密码是否是8-20个数字
        if not re.match(r'^[0-9A-Za-z]{8,20}$', password):
            return http.HttpResponseForbidden('密码最少8位,最长20位')

        # 认证登录用户
        user = authenticate(username=username, password=password)
        if user is None:
            return render(request, 'login.html', {'account_errmsg': '用户名或密码错误'})

        # 实现状态保持
        login(request, user)
        # 设置状态保持的周期
        if remembered != 'on':
            # 没有记住用户:浏览器会话结束就过期
            request.session.set_expiry(0)
        else:
            # 记住用户:None表示两周后过期
            request.session.set_expiry(None)

        # 响应登录结果
        return redirect(reverse('contents:index'))

多账号登录

  • Django自带的用户认证后端默认是使用用户名实现用户认证的。

  • 用户认证后端位置:django.contrib.auth.backends.ModelBackend。

  • 如果想实现用户名和手机号都可以认证用户,就需要自定义用户认证后端。

  • 自定义用户认证后端步骤

    • 在users应用中新建utils.py文件
    • 新建类,继承自ModelBackend
    • 重写认证authenticate()方法
    • 分别使用用户名和手机号查询用户
    • 返回查询到的用户实例                                

      1. 自定义用户认证后端 users.utils.py         

      • from django.contrib.auth.backends import ModelBackend
        import re
        from .models import User
        
        
        def get_user_by_account(account):
            """
            根据account查询用户
            :param account: 用户名或者手机号
            :return: user
            """
            try:
                if re.match('^1[3-9]\d{9}$', account):
                    # 手机号登录
                    user = User.objects.get(mobile=account)
                else:
                    # 用户名登录
                    user = User.objects.get(username=account)
            except User.DoesNotExist:
                return None
            else:
                return user
        
        
        class UsernameMobileAuthBackend(ModelBackend):
            """自定义用户认证后端"""
        
            def authenticate(self, request, username=None, password=None, **kwargs):
                """
                重写认证方法,实现多账号登录
                :param request: 请求对象
                :param username: 用户名
                :param password: 密码
                :param kwargs: 其他参数
                :return: user
                """
                # 根据传入的username获取user对象。username可以是手机号也可以是账号
                user = get_user_by_account(username)
                # 校验user是否存在并校验密码是否正确
                if user and user.check_password(password):
                    return user

        2. 配置自定义用户认证后端

      • 1.Django自带认证后端源码

         

         2.配置自定义用户认证后端 

      • # 指定自定义的用户认证后端
        AUTHENTICATION_BACKENDS = ['users.utils.UsernameMobileAuthBackend']
        1. Django自带的用户认证系统只会使用用户名去认证一个用户。
          • 所以我们为了实现多账号登录,就可以自定义认证后端,采用其他的唯一信息去认证一个用户。
          • 总结就是重写django认证,获取用户对象,判断如果能根据用户名或者手机号获取到用户信息,那么根据用户信息再进行检查密码是否正确,如果正确返回user对象,否则的话返回空值
posted @ 2021-05-19 22:15  lcsp  阅读(511)  评论(0编辑  收藏  举报