zoukankan      html  css  js  c++  java
  • 6、Django实战第6天:用户登录

    今天开始,我们需要来写后台逻辑了....

    后台逻辑代码都是编写在views.py文件里面,今天要完成的登录功能,因此来编辑users.views.py

    这里我们根据请求方法来判断分为2种情况,网页默认请求是的GET方法,当请求login函数(调用登录页面)方法为GET的时候(比如:访问login页面),则返回login的html页面

    from django.shortcuts import render
    
    
    def login(request):
        if request.method == 'POST':
            pass
        elif request.method == 'GET':
            return render(request, 'login.html', {})
    

    现在登录页面已经要走后台逻辑了,所以我们需要修改login的url配置

    ...
    from users.views import login
    
    urlpatterns = [
        #url(r'^admin/', admin.site.urls),
        url(r'^xadmin/', xadmin.site.urls),
        url(r'^$', TemplateView.as_view(template_name='index.html'), name='index'),
        url(r'^login/$', login, name='login'),
    ]

    修改完成后,访问登录页面127.0.0.1:8000/login也是正常的

    现在来关注POST方法,首先编辑login.html文件

     在users.views.py中打上断点

    然后开启Debug,访问登录页面127.0.0.1:8000/login,填写账号,密码,点击登录

    点击登录后,我们回到编辑器查看断点, 可以看到post已经获取到数据(账号,密码)

    获取到数据之后,我们就需要把它们提取出来,编辑users.views.py

    from django.shortcuts import render
    
    
    def login(request):
        if request.method == 'POST':
            user_name = request.POST.get('username', '')   #第一个参数是表单input的名字,
            pass_word = request.POST.get('password', '')    #第二个参数表示没取到则为空值
        elif request.method == 'GET':
            return render(request, 'login.html', {})
    

      

    当我们获取到用户名和密码之后,就需要去验证是否合法,我们这里需要用到Django提供的auth方法

    from django.shortcuts import render
    from django.contrib.auth import authenticate, login
    
    
    def user_login(request):    #因为我们上面导入了login,为了避免名字冲突,我们这里改用user_login
        if request.method == 'POST':
            user_name = request.POST.get('username', '')
            pass_word = request.POST.get('password', '')
            user = authenticate(username=user_name, password=pass_word) #对比数据表的账号密码
            if user is not None:   #如果user不为空,则验证通过
                login(request, user)   #使用login模块进行登录
                return render(request, 'index.html') #返回登录状态的首页(在首页做判断,登录前和登陆后显示不一样)
            else:
                return render(request, 'login.html', {}) #如果验证不通过则返回登录页面
        elif request.method == 'GET':
            return render(request, 'login.html', {})

    上面我们把login函数名改成了user_login, 因为url那里也要改

    import xadmin
    from django.views.generic import TemplateView
    from users.views import user_login
    
    urlpatterns = [
        #url(r'^admin/', admin.site.urls),
        url(r'^xadmin/', xadmin.site.urls),
        url(r'^$', TemplateView.as_view(template_name='index.html'), name='index'),
        url(r'^login/$', user_login, name='login'),
    ]

    修改index.html做一个判断,登录前和登录后是不同的显示

    现在,我们可以用之前创建的超级用户admin(admin123456)去登录,会成功跳转到登录后的首页,如果输入错误的账号或密码则是调到登录页面。因为现在还没有做退出登录操作,因为要想退出登录,可以先进去xadmin后台管理系统,然后注销就可以了

    到此,我们完成了以用户名的形式登录,如果想邮箱和用户名都可以登录,这里Django提供了一种方法,可以让我们自定义auth方法

    编辑users.views.py,定义CustomBackend类继承ModelBackend重载authenticate方法

    from django.contrib.auth.backends import ModelBackend
    
    from .models import UserProfile
    
    
    class CustomBackend(ModelBackend):
        def authenticate(self, username=None, password=None, **kwargs):
            try:
                user = UserProfile.objects.get(username=username) #判断用户名
                if user.check_password(password):   #检查明文密码
                    return user
            except Exception as e:
                return None

    还需要在settings.py中重载AUTHENTICATION_BACKENDS变量

    # Application definition
    AUTHENTICATION_BACKENDS = (
        'users.views.CustomBackend',
    )

    这样就完成了我们自定义的authenticate方法,以后user_login里面就会调用我们自己定义的authenticate方法

    当我们需要用用户名和邮箱都可以登录验证的时候,可以这样做

    from django.db.models import Q   #导入Q,可以使用并集查询
    
    from .models import UserProfile
    
    
    class CustomBackend(ModelBackend):
        def authenticate(self, username=None, password=None, **kwargs):
            try:
                user = UserProfile.objects.get(Q(username=username) | Q(email=username)) #判断用户名
                if user.check_password(password):   #检查明文密码
                    return user
            except Exception as e:
                return None

    现在我们用heboan@qq.com登录也可以登录成功了

    最后,当我们验证失败的时候,给用户提示信息(返回的时候,返回一个msg模板变量)

    def user_login(request):    #因为我们上面导入了login,为了避免名字冲突,我们这里改用user_login
        if request.method == 'POST':
            user_name = request.POST.get('username', '')
            pass_word = request.POST.get('password', '')
            user = authenticate(username=user_name, password=pass_word) #对比数据表的账号密码
            if user is not None:   #如果user不为空,则验证通过
                login(request, user)   #使用login模块进行登录
                return render(request, 'index.html') #返回登录状态的首页(在首页做判断,登录前和登陆后显示不一样)
            else:
                return render(request, 'login.html', {'msg': '用户名或密码错误'}) #如果验证不通过则返回登录页面
        elif request.method == 'GET':
            return render(request, 'login.html', {})

    修改下login.html


     上面我们做的登录是基于函数,现在我们基于类来做,因为基于类的方法会给我们带来很多方便

    编辑users,views.py

    ...
    from django.views.generic.base import View
    
    
    class LoginView(View):
        def get(self, request):
            return render(request, 'login.html', {})
    
        def post(self, request):
            user_name = request.POST.get('username', '')
            pass_word = request.POST.get('password', '')
            user = authenticate(username=user_name, password=pass_word)
            if user is not None:
                login(request, user)
                return render(request, 'index.html')
            else:
                return render(request, 'login.html', {'msg': '用户名或密码错误'})

    相应的,url那边也要做修改

    ...
    from users.views import LoginView
    
    urlpatterns = [
        #url(r'^admin/', admin.site.urls),
        url(r'^xadmin/', xadmin.site.urls),
        url(r'^$', TemplateView.as_view(template_name='index.html'), name='index'),
        url(r'^login/$', LoginView.as_view(), name='login'),
    ]

    再次尝试登录,一切正常,这样我们可以把之前写的use_login删掉,完整的代码如下

    from django.shortcuts import render
    from django.contrib.auth import authenticate, login
    from django.contrib.auth.backends import ModelBackend
    from django.db.models import Q   #导入Q,可以使用并集查询
    from django.views.generic.base import View
    
    from .models import UserProfile
    
    
    class CustomBackend(ModelBackend):
        def authenticate(self, username=None, password=None, **kwargs):
            try:
                user = UserProfile.objects.get(Q(username=username) | Q(email=username)) #判断用户名
                if user.check_password(password):   #检查明文密码
                    return user
            except Exception as e:
                return None
    
    
    class LoginView(View):
        def get(self, request):
            return render(request, 'login.html', {})
    
        def post(self, request):
            user_name = request.POST.get('username', '')
            pass_word = request.POST.get('password', '')
            user = authenticate(username=user_name, password=pass_word)
            if user is not None:
                login(request, user)
                return render(request, 'index.html')
            else:
                return render(request, 'login.html', {'msg': '用户名或密码错误'})
  • 相关阅读:
    理解对象和对象的描述特性
    常用JS方法整理
    vue组件从开发到发布
    Mac OS X下安装Vue脚手架(vue-cli)
    前端开发中提到的“脚手架”到底指什么,CLI?gulp 和 gulp-cli有什么区别
    【Android Studio快捷键】之代码提示
    Linux安装vmtools
    VC 获取控制台窗体的句柄(hWnd)
    ym——物联网入口之中的一个Android蓝牙4.0
    Nginx 做系统的前端反向proxy
  • 原文地址:https://www.cnblogs.com/sellsa/p/8456401.html
Copyright © 2011-2022 走看看