refactor: 修改授权相关Model,Serializer,API结构

pull/8873/head
Jiangjie.Bai 2022-09-07 17:35:23 +08:00
parent 585ce6b46a
commit a27aeca2fd
13 changed files with 67 additions and 101 deletions

View File

@ -7,7 +7,7 @@ from common.utils import pretty_string
from common.utils.random import random_string from common.utils.random import random_string
from assets.models import Asset, Gateway, Domain, CommandFilterRule from assets.models import Asset, Gateway, Domain, CommandFilterRule
from users.models import User from users.models import User
from perms.serializers.base import ActionsField from perms.serializers.permission import ActionsField
__all__ = [ __all__ = [

View File

@ -6,7 +6,8 @@ from .. import const
from .base import INSTALLED_APPS, TEMPLATES from .base import INSTALLED_APPS, TEMPLATES
XPACK_DIR = os.path.join(const.BASE_DIR, 'xpack') XPACK_DIR = os.path.join(const.BASE_DIR, 'xpack')
XPACK_ENABLED = os.path.isdir(XPACK_DIR) # XPACK_ENABLED = os.path.isdir(XPACK_DIR)
XPACK_ENABLED = False
XPACK_TEMPLATES_DIR = [] XPACK_TEMPLATES_DIR = []
XPACK_CONTEXT_PROCESSOR = [] XPACK_CONTEXT_PROCESSOR = []

View File

@ -1,14 +0,0 @@
from rest_framework import status
from django.utils.translation import gettext_lazy as _
from common.exceptions import JMSException
class AdminIsModifyingPerm(JMSException):
status_code = status.HTTP_409_CONFLICT
default_detail = _('The administrator is modifying permissions. Please wait')
class CanNotRemoveAssetPermNow(JMSException):
status_code = status.HTTP_409_CONFLICT
default_detail = _('The authorization cannot be revoked for the time being')

View File

@ -183,22 +183,15 @@ class AssetPermissionFilter(PermissionBaseFilter):
if is_effective: if is_effective:
have_user_q = Q(users__isnull=False) | Q(user_groups__isnull=False) have_user_q = Q(users__isnull=False) | Q(user_groups__isnull=False)
have_asset_q = Q(assets__isnull=False) | Q(nodes__isnull=False) have_asset_q = Q(assets__isnull=False) | Q(nodes__isnull=False)
have_system_user_q = Q(system_users__isnull=False)
have_action_q = Q(actions__gt=0) have_action_q = Q(actions__gt=0)
queryset = queryset.filter( queryset = queryset.filter(have_user_q & have_asset_q & have_action_q)
have_user_q & have_asset_q & have_system_user_q & have_action_q
)
queryset &= AssetPermission.objects.valid() queryset &= AssetPermission.objects.valid()
else: else:
not_have_user_q = Q(users__isnull=True) & Q(user_groups__isnull=True) not_have_user_q = Q(users__isnull=True) & Q(user_groups__isnull=True)
not_have_asset_q = Q(assets__isnull=True) & Q(nodes__isnull=True) not_have_asset_q = Q(assets__isnull=True) & Q(nodes__isnull=True)
not_have_system_user_q = Q(system_users__isnull=True)
not_have_action_q = Q(actions=0) not_have_action_q = Q(actions=0)
queryset = queryset.filter( queryset = queryset.filter(not_have_user_q | not_have_asset_q | not_have_action_q)
not_have_user_q | not_have_asset_q | not_have_system_user_q |
not_have_action_q
)
queryset |= AssetPermission.objects.invalid() queryset |= AssetPermission.objects.invalid()
return queryset return queryset

View File

@ -89,6 +89,11 @@ class AssetPermission(OrgModelMixin):
user_groups = models.ManyToManyField('users.UserGroup', blank=True, verbose_name=_("User group"), related_name='%(class)ss') user_groups = models.ManyToManyField('users.UserGroup', blank=True, verbose_name=_("User group"), related_name='%(class)ss')
assets = models.ManyToManyField('assets.Asset', related_name='granted_by_permissions', blank=True, verbose_name=_("Asset")) assets = models.ManyToManyField('assets.Asset', related_name='granted_by_permissions', blank=True, verbose_name=_("Asset"))
nodes = models.ManyToManyField('assets.Node', related_name='granted_by_permissions', blank=True, verbose_name=_("Nodes")) nodes = models.ManyToManyField('assets.Node', related_name='granted_by_permissions', blank=True, verbose_name=_("Nodes"))
# 只保存 @ALL (@INPUT @USER 默认包含,将来在全局设置中进行控制)
# 特殊的账号描述
# ['@ALL',]
# 指定账号授权
# ['web', 'root',]
accounts = models.JSONField(default=list, verbose_name=_("Accounts")) accounts = models.JSONField(default=list, verbose_name=_("Accounts"))
actions = models.IntegerField(choices=Action.DB_CHOICES, default=Action.ALL, verbose_name=_("Actions")) actions = models.IntegerField(choices=Action.DB_CHOICES, default=Action.ALL, verbose_name=_("Actions"))
is_active = models.BooleanField(default=True, verbose_name=_('Active')) is_active = models.BooleanField(default=True, verbose_name=_('Active'))

View File

@ -1,4 +1,5 @@
# coding: utf-8 # coding: utf-8
# #
from .base import * from .permission import *
from .asset import * from .permission_relation import *
from .user_permission import *

View File

@ -1,3 +0,0 @@
from .permission import *
from .permission_relation import *
from .user_permission import *

View File

@ -1,56 +0,0 @@
from rest_framework import serializers
from perms.models import Action
from orgs.mixins.serializers import BulkOrgResourceModelSerializer
from rest_framework.fields import empty
__all__ = ['ActionsDisplayField', 'ActionsField', 'BasePermissionSerializer']
class ActionsField(serializers.MultipleChoiceField):
def __init__(self, *args, **kwargs):
kwargs['choices'] = Action.CHOICES
super().__init__(*args, **kwargs)
def run_validation(self, data=empty):
data = super(ActionsField, self).run_validation(data)
if isinstance(data, list):
data = Action.choices_to_value(value=data)
return data
def to_representation(self, value):
return Action.value_to_choices(value)
def to_internal_value(self, data):
if not self.allow_empty and not data:
self.fail('empty')
if not data:
return data
return Action.choices_to_value(data)
class ActionsDisplayField(ActionsField):
def to_representation(self, value):
values = super().to_representation(value)
choices = dict(Action.CHOICES)
return [choices.get(i) for i in values]
class BasePermissionSerializer(BulkOrgResourceModelSerializer):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.set_actions_field()
def set_actions_field(self):
actions = self.fields.get('actions')
if not actions:
return
choices = actions._choices
choices = self._filter_actions_choices(choices)
actions._choices = choices
actions.default = list(choices.keys())
def _filter_actions_choices(self, choices):
return choices

View File

@ -2,50 +2,89 @@
# #
from rest_framework import serializers from rest_framework import serializers
from rest_framework.fields import empty
from django.utils.translation import ugettext_lazy as _ from django.utils.translation import ugettext_lazy as _
from django.db.models import Q from django.db.models import Q
from perms.models import AssetPermission, Action
from assets.models import Asset, Node from assets.models import Asset, Node
from users.models import User, UserGroup from users.models import User, UserGroup
from ..base import ActionsField, BasePermissionSerializer from perms.models import AssetPermission, Action
from orgs.mixins.serializers import BulkOrgResourceModelSerializer
__all__ = ['AssetPermissionSerializer'] __all__ = ['AssetPermissionSerializer', 'ActionsField']
class AssetPermissionSerializer(BasePermissionSerializer): class ActionsField(serializers.MultipleChoiceField):
def __init__(self, **kwargs):
kwargs['choices'] = Action.CHOICES
super().__init__(**kwargs)
def run_validation(self, data=empty):
data = super(ActionsField, self).run_validation(data)
if isinstance(data, list):
data = Action.choices_to_value(value=data)
return data
def to_representation(self, value):
return Action.value_to_choices(value)
def to_internal_value(self, data):
if not self.allow_empty and not data:
self.fail('empty')
if not data:
return data
return Action.choices_to_value(data)
class ActionsDisplayField(ActionsField):
def to_representation(self, value):
values = super().to_representation(value)
choices = dict(Action.CHOICES)
return [choices.get(i) for i in values]
class AssetPermissionSerializer(BulkOrgResourceModelSerializer):
users_display = serializers.ListField(
child=serializers.CharField(), label=_('Users display'), required=False
)
user_groups_display = serializers.ListField(
child=serializers.CharField(), label=_('User groups display'), required=False
)
assets_display = serializers.ListField(
child=serializers.CharField(), label=_('Assets display'), required=False
)
nodes_display = serializers.ListField(
child=serializers.CharField(), label=_('Nodes display'), required=False
)
actions = ActionsField(required=False, allow_null=True, label=_("Actions")) actions = ActionsField(required=False, allow_null=True, label=_("Actions"))
is_valid = serializers.BooleanField(read_only=True, label=_("Is valid")) is_valid = serializers.BooleanField(read_only=True, label=_("Is valid"))
is_expired = serializers.BooleanField(read_only=True, label=_('Is expired')) is_expired = serializers.BooleanField(read_only=True, label=_('Is expired'))
users_display = serializers.ListField(child=serializers.CharField(), label=_('Users display'), required=False)
user_groups_display = serializers.ListField(child=serializers.CharField(), label=_('User groups display'), required=False)
assets_display = serializers.ListField(child=serializers.CharField(), label=_('Assets display'), required=False)
nodes_display = serializers.ListField(child=serializers.CharField(), label=_('Nodes display'), required=False)
class Meta: class Meta:
model = AssetPermission model = AssetPermission
fields_mini = ['id', 'name'] fields_mini = ['id', 'name']
fields_small = fields_mini + [ fields_small = fields_mini + [
'is_active', 'is_expired', 'is_valid', 'actions', 'is_active', 'is_expired', 'is_valid', 'actions',
'accounts',
'created_by', 'date_created', 'date_expired', 'created_by', 'date_created', 'date_expired',
'date_start', 'comment', 'from_ticket' 'date_start', 'comment', 'from_ticket'
] ]
fields_m2m = [ fields_m2m = [
'users', 'users_display', 'user_groups', 'user_groups_display', 'assets', 'users', 'users_display', 'user_groups', 'user_groups_display', 'assets',
'assets_display', 'nodes', 'nodes_display', 'accounts', 'assets_display', 'nodes', 'nodes_display',
'users_amount', 'user_groups_amount', 'assets_amount', 'users_amount', 'user_groups_amount', 'assets_amount',
'nodes_amount', 'nodes_amount',
] ]
fields = fields_small + fields_m2m fields = fields_small + fields_m2m
read_only_fields = ['created_by', 'date_created', 'from_ticket'] read_only_fields = ['created_by', 'date_created', 'from_ticket']
extra_kwargs = { extra_kwargs = {
'is_expired': {'label': _('Is expired')},
'is_valid': {'label': _('Is valid')},
'actions': {'label': _('Actions')},
'users_amount': {'label': _('Users amount')}, 'users_amount': {'label': _('Users amount')},
'user_groups_amount': {'label': _('User groups amount')}, 'user_groups_amount': {'label': _('User groups amount')},
'assets_amount': {'label': _('Assets amount')}, 'assets_amount': {'label': _('Assets amount')},
'nodes_amount': {'label': _('Nodes amount')}, 'nodes_amount': {'label': _('Nodes amount')},
'actions': {'label': _('Actions')},
'is_expired': {'label': _('Is expired')},
'is_valid': {'label': _('Is valid')},
} }
@classmethod @classmethod

View File

@ -5,7 +5,7 @@ from rest_framework import serializers
from django.utils.translation import ugettext_lazy as _ from django.utils.translation import ugettext_lazy as _
from assets.models import Node, Asset, Platform from assets.models import Node, Asset, Platform
from perms.serializers.base import ActionsField from perms.serializers.permission import ActionsField
__all__ = [ __all__ = [
'NodeGrantedSerializer', 'NodeGrantedSerializer',

View File

@ -2,7 +2,7 @@ from django.utils.translation import ugettext as _
from rest_framework import serializers from rest_framework import serializers
from perms.models import ApplicationPermission from perms.models import ApplicationPermission
from perms.serializers.base import ActionsField from perms.serializers.permission import ActionsField
from orgs.utils import tmp_to_org from orgs.utils import tmp_to_org
from applications.models import Application from applications.models import Application
from tickets.models import ApplyApplicationTicket from tickets.models import ApplyApplicationTicket

View File

@ -1,7 +1,7 @@
from django.utils.translation import ugettext_lazy as _ from django.utils.translation import ugettext_lazy as _
from rest_framework import serializers from rest_framework import serializers
from perms.serializers.base import ActionsField from perms.serializers.permission import ActionsField
from perms.models import AssetPermission from perms.models import AssetPermission
from orgs.utils import tmp_to_org from orgs.utils import tmp_to_org
from assets.models import Asset, Node from assets.models import Asset, Node