Django-simpleui的菜單權(quán)限配置,實(shí)現(xiàn)無權(quán)限不顯示菜單
作者:小小IT仔
當(dāng)我們使用Django+simpleui這個(gè)框架的時(shí)候,如果想實(shí)現(xiàn)當(dāng)某個(gè)用戶沒有某個(gè)菜單的權(quán)限時(shí),他無法在界面上看到這個(gè)菜單,在不改變源碼的情況下是無法實(shí)現(xiàn)的。
聊聊需求
當(dāng)我們使用Django+simpleui這個(gè)框架的時(shí)候,如果想實(shí)現(xiàn)當(dāng)某個(gè)用戶沒有某個(gè)菜單的權(quán)限時(shí),他無法在界面上看到這個(gè)菜單,在不改變源碼的情況下是無法實(shí)現(xiàn)的,換句話說就是無法直接實(shí)現(xiàn)根據(jù)權(quán)限顯示或隱藏菜單。
解決辦法-修改simpleui的源代碼
需求:Django-simpleui實(shí)現(xiàn)根據(jù)用戶權(quán)限顯示或者隱藏菜單
- 修改模塊:simpletags.py
- 路徑:...XXX\venv\Lib\site-packages\simpleui\templatetags\simpletags.py(根據(jù)你的項(xiàng)目確定路徑,一般為虛擬環(huán)境)
第一步:注釋原有的菜單模塊:
# app_list = context.get('app_list')
# for app in app_list:
# _models = [
# {
# 'name': m.get('name'),
# 'icon': get_icon(m.get('object_name'), unicode_to_str(m.get('name'))),
# 'url': m.get('admin_url'),
# 'addUrl': m.get('add_url'),
# 'breadcrumbs': [{
# 'name': app.get('name'),
# 'icon': get_icon(app.get('app_label'), app.get('name'))
# }, {
# 'name': m.get('name'),
# 'icon': get_icon(m.get('object_name'), unicode_to_str(m.get('name')))
# }]
# }
#
# for m in app.get('models')
# ] if app.get('models') else []
#
# module = {
# 'name': app.get('name'),
# 'icon': get_icon(app.get('app_label'), app.get('name')),
# 'models': _models
# }
# data.append(module)
第二步:讀取SIMPLEUI_CONFIG設(shè)置合并菜單處理:
...
# 如果有menu 就讀取,沒有就調(diào)用系統(tǒng)的
key = 'system_keep'
# if config and 'menus' in config:
# if config.get(key, None):
# temp = config.get('menus')
# for i in temp:
# # 處理面包屑
# if 'models' in i:
# for k in i.get('models'):
# k['breadcrumbs'] = [{
# 'name': i.get('name'),
# 'icon': i.get('icon')
# }, {
# 'name': k.get('name'),
# 'icon': k.get('icon')
# }]
# else:
# i['breadcrumbs'] = [{
# 'name': i.get('name'),
# 'icon': i.get('icon')
# }]
# data.append(i)
# else:
# data = config.get('menus')
# 修改為
if config and 'menus' in config:
total = config.get('menus')
group_permissions = len(context.request.user.get_group_permissions())
user_permissions = len(context.request.user.get_user_permissions())
if (group_permissions > user_permissions):
user_permissions = context.request.user.get_group_permissions().union(
context.request.user.get_user_permissions())
else:
user_permissions = context.request.user.get_group_permissions().union(
context.request.user.get_user_permissions())
for level_one_menu in total:
# 與一級菜單codename比對權(quán)限
if 'codename' not in level_one_menu or (
True in [(True if level_one_menu['codename'] in u_p else False) for u_p in
user_permissions]) == False:
if context.request.user.is_superuser == False:
continue
# 處理面包屑
if 'models' in level_one_menu:
del_models = list()
for level_two_menu in level_one_menu.get('models'):
if context.request.user.is_superuser:
pass
elif 'codename' not in level_two_menu.keys():
del_models.append(level_two_menu)
continue
elif ('codename' not in level_one_menu or 'codename' not in level_two_menu
or (level_one_menu['codename'] + '.' + level_two_menu[
'codename'] not in user_permissions)) and \
(level_one_menu['codename'] + '.view_' + level_two_menu['codename'] not in user_permissions) \
and (
level_one_menu['codename'] + '.add_' + level_two_menu['codename'] not in user_permissions) \
and (level_one_menu['codename'] + '.change_' + level_two_menu[
'codename'] not in user_permissions) \
and (level_one_menu['codename'] + '.delete_' + level_two_menu[
'codename'] not in user_permissions) \
and level_two_menu['codename'] not in user_permissions:
del_models.append(level_two_menu)
continue
level_two_menu['breadcrumbs'] = [{
'name': level_one_menu.get('name'),
'icon': level_one_menu.get('icon')
}, {
'name': level_two_menu.get('name'),
'icon': level_two_menu.get('icon')
}]
for del_m in del_models:
level_one_menu['models'].remove(del_m)
else:
level_one_menu['breadcrumbs'] = [{
'name': level_one_menu.get('name'),
'icon': level_one_menu.get('icon')
}]
if len(level_one_menu['models']) > 0:
data.append(level_one_menu)
else:
data = config.get('menus')
...
# 獲取側(cè)邊欄排序, 如果設(shè)置了就按照設(shè)置的內(nèi)容排序, 留空則表示默認(rèn)排序以及全部顯示
# if config.get('menu_display') is not None:
# display_data = list()
# for _app in data:
# if _app['name'] not in config.get('menu_display'):
# continue
# _app['_weight'] = config.get('menu_display').index(_app['name'])
# display_data.append(_app)
# display_data.sort(key=lambda x: x['_weight'])
# data = display_data
# 修改
if config.get('menu_display') is not None:
display_data = list()
for _app in data:
if _app['name'] not in config.get('menu_display'):
continue
# 處理二級菜單顯示權(quán)限
if _app.get('menu_display') is not None:
display_model = list()
for _app_m in _app['models']:
if _app_m['name'] not in _app.get('menu_display'):
continue
# 沒有排序邏輯,這里的_weight暫時(shí)無效
_app['_weight'] = config.get('menu_display').index(_app['name'])
display_data.append(_app)
else:
display_model = _app['models']
_app['models'] = display_model
_app['_weight'] = config.get('menu_display').index(_app['name'])
display_data.append(_app)
display_data.sort(key=lambda x: x['_weight'])
data = display_data
...
第三步:修改setting.py中的菜單配置。
注意:
- 配置中一級菜單中的codename一般為app名字,二級菜單的codename一般為模型中的類名;
- 只填寫一級菜單的codename或不填一級菜單和二級菜單的codename,表示該只允許superuser查看。
...
SIMPLEUI_CONFIG = {
'system_keep': False, # 關(guān)閉系統(tǒng)菜單
'dynamic': True, # 設(shè)置是否開啟動(dòng)態(tài)菜單, 默認(rèn)為False. 如果開啟, 則會(huì)在每次用戶登陸時(shí)動(dòng)態(tài)展示菜單內(nèi)容
'menus': [
# 菜單1
{
'app': 'app_article_ad',
'codename' : 'app_article_ad',
'name': '公眾號文章',
'icon': 'fas fa-user-shield',
'models': [
{
'name': '文章管理',
'codename':'job_article',
'icon': 'fa fa-user',
'url': 'app_article_ad/job_article/'
},
]
},
# 菜單2
{
'app': 'app_files',
'codename': 'app_files',
'name': '資源管理',
'icon': 'fas fa-user-shield',
'models': [
{
'name': '文件管理',
'codename': 'file',
'icon': 'fa fa-user',
'url': '/app_files/file_list'
},
]
},
...
修改
if config.get('menu_display') is not None:
display_data = list()
for _app in data:
if _app['name'] not in config.get('menu_display'):
continue
# 處理二級菜單顯示權(quán)限
if _app.get('menu_display') is not None:
display_model = list()
for _app_m in _app['models']:
if _app_m['name'] not in _app.get('menu_display'):
continue
# 沒有排序邏輯,這里的_weight暫時(shí)無效
_app['_weight'] = config.get('menu_display').index(_app['name'])
display_data.append(_app)
else:
display_model = _app['models']
_app['models'] = display_model
_app['_weight'] = config.get('menu_display').index(_app['name'])
display_data.append(_app)
display_data.sort(key=lambda x: x['_weight'])
data = display_data
效果
管理員界面
普通用戶界面
責(zé)任編輯:趙寧寧
來源:
IT仔的筆記本