Django有一个内置的受权系统:包括验证和受权两个部分。用来处理用户、分组、权限以及基于cookie的会话系统。html
验证:验证这个用户是不是他声称的人(好比用户名和密码验证,角色验证)python
受权:给与他相应的权限。数据库
Django内置的权限系统:django
受权系统:默认中建立完一个django项目后,就已经集成了受权系统。cookie
INSTALLED_APPS:session
中间件:框架
SessionMiddleware:用来管理session。
AuthenticationMiddleware:用来处理和当前session相关联的用户。post
User模型
网站
该框架的核心部分。完整的路径 django.contrib.auth.models.User ui
内置的User模型拥有的字段:
基本用法:
1 from django.http import HttpResponse 2 from django.contrib.auth.models import User 3 4 def index(request): 5 # 建立普通用户 6 user = User.objects.create_user(username='jack',email='jack@123.com',password='111111') 7 # 建立超级用户 8 user = User.objects.create_superuser(username='Alen', email='Alen@123.com', password='111111') 9 return HttpResponse('success')
修改密码:
密码是须要通过加密后才能存储进去的。不能直接修改 password 字段,须要调用 set_password 来修改密码。
1 user = User.objects.get(pk=1) 2 user.set_password('填写新密码') 3 user.save()
登陆验证:
Django的验证系统已经经过 django.contrib.auth.authenticate 实现了登陆验证的功能。该方法只能经过 username 和 password 来进行验证。
1 from django.contrib.auth import authenticate 2 3 def index(request): 4 username = 'jack' 5 password = '111111' 6 user = authenticate(request,username=username,password=password) 7 if user: 8 print('登陆成功:%s'% username) 9 else: 10 print('用户名或密码错误!') 11 return HttpResponse('success')
扩展用户模型:
在验证用户登陆的时候,用的是用户名做为验证,而有时候须要经过手机号码或者邮箱来进行验证。或者须要增长一些新的字段。这时就须要扩展用户模型。
1 from django.db import models 2 from django.contrib.auth.models import User 3 4 # 使用代理模型,不能添加新的Field;可加新属性; 5 class Person(User): 6 class Meta: 7 proxy = True 8 #增长黑名单属性; 9 @classmethod 10 def get_blacklsit(cls): 11 return cls.objects.filter(is_active=False)
1 from .models import Person 2 from django.contrib.auth.models import User 3 from django.http import HttpResponse 4 5 # 提取数据表单中“is_active=0”的黑名单数据;(‘auth_user’表单已存储数据) 6 def get_blacklist(request): 7 black_list = Person.get_blacklsit() 8 for person in black_list: 9 print(person.username) 10 return HttpResponse('proxy')
定义了一个 Person类 ,继承自 User ,Meta 中设置 proxy=True ,说明这只是 User 的一个代理模型。不影响原来User模型在数据库中表的结构。且 User.objects.all() 和 Person.objects.all() 是等价的。都是从User这个模型中获取全部的数据。
1 from django.db import models 2 from django.contrib.auth.models import User 3 from django.dispatch import receiver 4 from django.db.models.signals import post_save 5 6 # 使用一对一外键扩展 7 class UserExtension(models.Model): 8 user = models.OneToOneField(User,on_delete=models.CASCADE,related_name='extension') 9 telephone = models.CharField(max_length=11) 10 school = models.CharField(max_length=100) 11 12 # @receiver:用于将接收器链接到信号的装饰器。经过传入使用信号(或信号列表)和链接的关键字参数; 13 # sender:发送者 ; instance:调用save的实例 ; created:是不是新建立的; 14 # 接收User的save信号; 15 @receiver(post_save,sender=User) 16 def handler_user_extension(sender,instance,created,**kwargs): 17 if created: 18 UserExtension.objects.create(user=instance) 19 else: 20 instance.extension.save()
1 from django.shortcuts import render 2 from django.http import HttpResponse 3 from django.contrib.auth import authenticate 4 from .models import UserExtension 5 from django.contrib.auth.models import User 6 7 # 自定义验证号码及密码; 8 def my_authenticate(telephone,password): 9 user = User.objects.filter(extension__telephone=telephone).first() 10 if user: 11 is_correct = user.check_password(password) 12 if is_correct: 13 return user 14 else: 15 return None 16 else: 17 return None 18 19 def one_view(request): 20 # 建立用户,使用外键反向引用添加telephone; 21 # user = User.objects.create_user(username='three',password='111111',email='three@123.com') 22 # user.extension.telephone = '18988889999' 23 # user.save() 24 # 进行验证; 25 telephone = request.GET.get('telephone') 26 password = request.GET.get('password') 27 user = my_authenticate(telephone,password) 28 if user: 29 print('%s:验证成功'% user.username) 30 else: 31 print('用户验证失败!') 32 return HttpResponse('success')
定义一个 UserExtension的模型 与 User模型 进行一对一的绑定,之后新增的字段,就添加到 UserExtension 上。建立一个接受保存模型的信号处理方法,只要 User 调用了 save 方法,就会建立一个 UserExtension 和 User 进行绑定。
登陆、注销和登陆限制
登陆用户:
1 from django.contrib.auth import login 2 3 def my_login(request): 4 if request.method == 'GET': 5 return render(request,'login.html') 6 else: 7 form = LoginForm(request.POST) 8 if form.is_valid(): 9 telephone = form.cleaned_data.get('telephone') 10 password = form.cleaned_data.get('password') 11 remember = form.cleaned_data.get('remember') 12 user = my_authenticate(telephone=telephone,password=password) 13 if user and user.is_active: 14 # 判断经过时登陆成功,会生成session数据;再判断是否记住数据; 15 login(request,user) 16 if remember: 17 request.session.set_expiry(None) 18 else: 19 request.session.set_expiry(0) 20 # 定义获取next时的跳转页面 21 next_url = request.GET.get('next') 22 if next_url: 23 return redirect(next_url) 24 else: 25 return HttpResponse('登陆成功') 26 else: 27 return HttpResponse('手机号或密码错误!') 28 else: 29 print(form.errors) 30 return redirect(reverse('login'))
1 <!--login.html--> 2 <tr> 3 <td> 4 <label for=""> 5 <input type="checkbox" name="remember" value="1">记住密码 6 </label> 7 </td> 8 </tr>
注销用户:
1 from django.contrib.auth import logout 2 3 # 注销用户 4 def my_logout(request): 5 logout(request) 6 return HttpResponse('退出登陆')
登陆限制:
1 from django.contrib.auth.decorators import login_required 2 3 # 登陆限制,验证失败是会跳转到‘/login/’的url页面; 4 @login_required(login_url='/login/') 5 def profile(request): 6 return HttpResponse('我的中心,登陆才能查看!')