low版权限管理结构
图片.png1.创建rbac应用
1.先看配置文件合适不,给创建的rbac在配置文件里面设置一下找到
INSTTLED_APPs=['rbac']
图片.png
2.配置静态文件
图片.png
2.在models中创建对象
models
from django.db import models
class Permission(models.Model):
"""
权限表
"""
title = models.CharField(verbose_name='标题',max_length=32)
url = models.CharField(verbose_name="含正则URL",max_length=64)
is_menu = models.BooleanField(verbose_name="是否是菜单")
class Meta:
verbose_name_plural = "权限表"
def __str__(self):
return self.title
class User(models.Model):
"""
用户表
"""
username = models.CharField(verbose_name='用户名',max_length=32)
password = models.CharField(verbose_name='密码',max_length=64)
email = models.CharField(verbose_name='邮箱',max_length=32)
roles = models.ManyToManyField(verbose_name='具有的所有角色',to="Role",blank=True)
class Meta:
verbose_name_plural = "用户表"
def __str__(self):
return self.username
class Role(models.Model):
"""
角色表
"""
title = models.CharField(max_length=32)
permissions = models.ManyToManyField(verbose_name='具有的所有权限',to='Permission',blank=True)
class Meta:
verbose_name_plural = "角色表"
def __str__(self):
return self.title
models
3.基于Django admin录入权限数据
注意录入信息要先创建个超级用户
python3 manage.py createsuperuser
-用户名 root
-密码:peak2345
注意;需要在admin.py中做如下操作(只针对从用admin导入数据的时候配置,当然也可以直接添加)
from django.contrib import admin
from . import models
admin.site.register(models.Permission)
admin.site.register(models.User)
admin.site.register(models.Role)
4.用户登录程序
根据输入的用户名和密码的到相应的user
根据user对象获取其拥有的角色和权限并去重并将权限表的url放入session中,将这部分操作的代码抽取到service包下的init_permission.py下的init_permission(request,user)方法中,然后在views中调用该方法既可
- 获取当前用户具有的所有权限(去重)
- 获取权限中的url,放置到session中
def init_permission(user,request):
"""
初始化权限信息,获取权限信息并放置到session中。
:param user:
:param request:
:return:
"""
permission_list = user.roles.values('permissions__title', 'permissions__url', 'permissions__is_menu').distinct()
url_list = []
for item in permission_list:
url_list.append(item['permissions__url'])
print(url_list)
request.session['permission_url_list'] = url_list
init_permission.py
4.中间件的使用
如果不用中间件会有好多个函数,就有许多重复的代码,这样我们可以用中间件来完成
中间件和装饰器的区别:
- 中间件用来做批量处理
- 如果函数不多的话可以用加装饰器的方法
import re
#:用re去匹配的时候,re.match(/userinfo/,/userinfo/add) #都能匹配到
from django.shortcuts import redirect,HttpResponse
from django.conf import settings
class MiddlewareMixin(object):
def __init__(self, get_response=None):
self.get_response = get_response
super(MiddlewareMixin, self).__init__()
def __call__(self, request):
response = None
if hasattr(self, 'process_request'):
response = self.process_request(request)
if not response:
response = self.get_response(request)
if hasattr(self, 'process_response'):
response = self.process_response(request, response)
return response
class RbacMiddleware(MiddlewareMixin):
def process_request(self,request):
# 1. 获取当前请求的URL
# request.path_info
# 2. 获取Session中保存当前用户的权限
# request.session.get("permission_url_list')
current_url = request.path_info
# 当前请求不需要执行权限验证(白名单)
for url in settings.VALID_URL:
if re.match(url,current_url):
return None
permission_list = request.session.get("permission_url_list")
if not permission_list:
return redirect('/login/')
flag = False
for db_url in permission_list:
regax = "^{0}$".format(db_url)
#:那么要记得在匹配正则的时候加个起始符和终止符regex = "^{0}$".format(url)
if re.match(regax, current_url):
flag = True
break
if not flag:
return HttpResponse('无权访问')
rbac.py
a.获取当前访问的路径 request.path_info
b.在setting中配置不需要验证的url--白名单(人人登录后都能访问如login admin)然后调用
VALID_URL = [
"/login/",
"/admin.*"
]
根据正则判断当前路径是否在白名单中,白名单中的路径要严格控制以什么开头和什么结尾,如果有白名单return none继续执行后面代码如果不是直接跳转到登录
c.不是白名单的话,则要判断是否登录,最简单的方法就是获取session
看里面是否为空,如果为空的话说明没有登录直接跳转到登录,不让他执行后续的操作
d.url list不为空的话就说明已经登陆了,进一步看当前的访问路径是否在是否在urllist中,在的话就说明用户具有操作该url的权限否则就说明该用户没有
访问权限,直接return HttpResponse("无权访问")
注意:中间件创建完成之后。需要在settings中的MIDDLEWARE最后添加'rbac.middlewares.rbac.RbacMiddleware',
MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
'rbac.middlewares.rbac.RbacMiddleware',
]
网友评论