mirror of https://github.com/jumpserver/jumpserver
Merge branch 'v3' of github.com:jumpserver/jumpserver into v3
commit
f223cf43cc
|
@ -9,6 +9,10 @@ __all__ = ['Account', 'AccountTemplate']
|
|||
|
||||
|
||||
class Account(BaseAccount):
|
||||
class InnerAccount(models.TextChoices):
|
||||
INPUT = '@INPUT', '@INPUT'
|
||||
USER = '@USER', '@USER'
|
||||
|
||||
asset = models.ForeignKey(
|
||||
'assets.Asset', related_name='accounts',
|
||||
on_delete=models.CASCADE, verbose_name=_('Asset')
|
||||
|
@ -40,6 +44,16 @@ class Account(BaseAccount):
|
|||
def __str__(self):
|
||||
return '{}@{}'.format(self.username, self.asset.name)
|
||||
|
||||
@classmethod
|
||||
def get_input_account(cls):
|
||||
""" @INPUT 手动登录的账号(any) """
|
||||
return cls(name=cls.InnerAccount.INPUT.value, username='')
|
||||
|
||||
@classmethod
|
||||
def get_user_account(cls, username):
|
||||
""" @USER 动态用户的账号(self) """
|
||||
return cls(name=cls.InnerAccount.USER.value, username=username)
|
||||
|
||||
|
||||
class AccountTemplate(BaseAccount):
|
||||
class Meta:
|
||||
|
|
|
@ -4,8 +4,6 @@
|
|||
|
||||
import logging
|
||||
import uuid
|
||||
from functools import reduce
|
||||
from collections import Iterable
|
||||
|
||||
from django.db import models
|
||||
from django.db.models import Q
|
||||
|
@ -180,9 +178,11 @@ class Asset(AbsConnectivity, NodesRelationMixin, JMSOrgBaseModel):
|
|||
return tree_node
|
||||
|
||||
def filter_accounts(self, account_names=None):
|
||||
from perms.models import AssetPermission
|
||||
if account_names is None:
|
||||
return self.accounts.all()
|
||||
assert isinstance(account_names, Iterable), '`account_names` must be an iterable object'
|
||||
if AssetPermission.SpecialAccount.ALL in account_names:
|
||||
return self.accounts.all()
|
||||
queries = Q(name__in=account_names) | Q(username__in=account_names)
|
||||
accounts = self.accounts.filter(queries)
|
||||
return accounts
|
||||
|
|
|
@ -19,7 +19,7 @@ from perms.utils.permission import (
|
|||
from common.permissions import IsValidUser
|
||||
from common.utils import get_logger, lazyproperty
|
||||
|
||||
from perms.hands import User, Asset
|
||||
from perms.hands import User, Asset, Account
|
||||
from perms import serializers
|
||||
from perms.models import AssetPermission
|
||||
|
||||
|
@ -150,7 +150,7 @@ class UserGrantedAssetAccounts(ListAPIView):
|
|||
}
|
||||
|
||||
@lazyproperty
|
||||
def user(self):
|
||||
def user(self) -> User:
|
||||
user_id = self.kwargs.get('pk')
|
||||
return User.objects.get(id=user_id)
|
||||
|
||||
|
@ -163,11 +163,14 @@ class UserGrantedAssetAccounts(ListAPIView):
|
|||
|
||||
def get_queryset(self):
|
||||
# 获取用户-资产的授权规则
|
||||
assetperms = AssetPermission.filter_permissions(self.user, self.asset)
|
||||
assetperms = AssetPermission.filter(self.user, self.asset)
|
||||
account_names = AssetPermission.get_account_names(assetperms)
|
||||
accounts = self.asset.filter_accounts(account_names)
|
||||
accounts = list(self.asset.filter_accounts(account_names))
|
||||
# @INPUT @USER
|
||||
inner_accounts = [Account.get_input_account(), Account.get_user_account(self.user.username)]
|
||||
all_accounts = accounts + inner_accounts
|
||||
# 构造默认包含的账号,如: @INPUT @USER
|
||||
return accounts
|
||||
return all_accounts
|
||||
|
||||
|
||||
class MyGrantedAssetAccounts(UserGrantedAssetAccounts):
|
||||
|
|
|
@ -2,12 +2,12 @@
|
|||
#
|
||||
|
||||
from users.models import User, UserGroup
|
||||
from assets.models import Asset, Node, Label, FavoriteAsset
|
||||
from assets.models import Asset, Node, Label, FavoriteAsset, Account
|
||||
from assets.serializers import NodeSerializer
|
||||
|
||||
__all__ = [
|
||||
'User', 'UserGroup',
|
||||
'Asset', 'Node', 'Label', 'FavoriteAsset',
|
||||
'NodeSerializer',
|
||||
'NodeSerializer', 'Account'
|
||||
]
|
||||
|
||||
|
|
|
@ -83,6 +83,9 @@ class AssetPermissionManager(OrgManager):
|
|||
|
||||
|
||||
class AssetPermission(OrgModelMixin):
|
||||
class SpecialAccount(models.TextChoices):
|
||||
ALL = '@ALL', 'All'
|
||||
|
||||
id = models.UUIDField(default=uuid.uuid4, primary_key=True)
|
||||
name = models.CharField(max_length=128, verbose_name=_('Name'))
|
||||
users = models.ManyToManyField('users.User', blank=True, verbose_name=_("User"),
|
||||
|
@ -113,11 +116,6 @@ class AssetPermission(OrgModelMixin):
|
|||
|
||||
objects = AssetPermissionManager.from_queryset(AssetPermissionQuerySet)()
|
||||
|
||||
class SpecialAccount(models.TextChoices):
|
||||
ALL = '@ALL', 'All'
|
||||
INPUT = '@INPUT', 'Input'
|
||||
USER = '@USER', 'User'
|
||||
|
||||
class Meta:
|
||||
unique_together = [('org_id', 'name')]
|
||||
verbose_name = _("Asset permission")
|
||||
|
@ -232,17 +230,17 @@ class AssetPermission(OrgModelMixin):
|
|||
return account_names
|
||||
|
||||
@classmethod
|
||||
def filter_permissions(cls, user=None, asset=None, account=None):
|
||||
def filter(cls, user=None, asset=None, account=None):
|
||||
""" 获取同时包含 用户-资产-账号 的授权规则 """
|
||||
assetperm_ids = []
|
||||
if user:
|
||||
user_assetperm_ids = cls.filter_permissions_by_user(user, flat=True)
|
||||
user_assetperm_ids = cls.filter_by_user(user, flat=True)
|
||||
assetperm_ids.append(user_assetperm_ids)
|
||||
if asset:
|
||||
asset_assetperm_ids = cls.filter_permissions_by_asset(asset, flat=True)
|
||||
asset_assetperm_ids = cls.filter_by_asset(asset, flat=True)
|
||||
assetperm_ids.append(asset_assetperm_ids)
|
||||
if account:
|
||||
account_assetperm_ids = cls.filter_permissions_by_account(account, flat=True)
|
||||
account_assetperm_ids = cls.filter_by_account(account, flat=True)
|
||||
assetperm_ids.append(account_assetperm_ids)
|
||||
# & 是同时满足,比如有用户,但是用户的规则是空,那么返回也应该是空
|
||||
assetperm_ids = list(reduce(lambda x, y: set(x) & set(y), assetperm_ids))
|
||||
|
@ -250,7 +248,7 @@ class AssetPermission(OrgModelMixin):
|
|||
return assetperms
|
||||
|
||||
@classmethod
|
||||
def filter_permissions_by_user(cls, user, with_group=True, flat=False):
|
||||
def filter_by_user(cls, user, with_group=True, flat=False):
|
||||
assetperm_ids = set()
|
||||
user_assetperm_ids = AssetPermission.users.through.objects \
|
||||
.filter(user_id=user.id) \
|
||||
|
@ -273,7 +271,7 @@ class AssetPermission(OrgModelMixin):
|
|||
return assetperms
|
||||
|
||||
@classmethod
|
||||
def filter_permissions_by_asset(cls, asset, with_node=True, flat=False):
|
||||
def filter_by_asset(cls, asset, with_node=True, flat=False):
|
||||
assetperm_ids = set()
|
||||
asset_assetperm_ids = AssetPermission.assets.through.objects \
|
||||
.filter(asset_id=asset.id) \
|
||||
|
@ -294,8 +292,9 @@ class AssetPermission(OrgModelMixin):
|
|||
return assetperms
|
||||
|
||||
@classmethod
|
||||
def filter_permissions_by_account(cls, account, flat=False):
|
||||
assetperms = cls.objects.filter(accounts__contains=account).valid()
|
||||
def filter_by_account(cls, account, flat=False):
|
||||
queries = Q(accounts__contains=account) | Q(accounts__contains=cls.SpecialAccount.ALL.value)
|
||||
assetperms = cls.objects.filter(queries).valid()
|
||||
if flat:
|
||||
assetperm_ids = assetperms.values_list('id', flat=True)
|
||||
return assetperm_ids
|
||||
|
|
Loading…
Reference in New Issue