mirror of https://github.com/jumpserver/jumpserver
commit
1d5e603c0d
|
@ -34,7 +34,7 @@ RUN pip install --upgrade pip==20.2.4 setuptools==49.6.0 wheel==0.34.2 -i ${PIP_
|
||||||
|
|
||||||
COPY --from=stage-build /opt/jumpserver/release/jumpserver /opt/jumpserver
|
COPY --from=stage-build /opt/jumpserver/release/jumpserver /opt/jumpserver
|
||||||
RUN mkdir -p /root/.ssh/ \
|
RUN mkdir -p /root/.ssh/ \
|
||||||
&& echo -e "Host *\n\tStrictHostKeyChecking no\n\tUserKnownHostsFile /dev/null" > /root/.ssh/config
|
&& echo "Host *\n\tStrictHostKeyChecking no\n\tUserKnownHostsFile /dev/null" > /root/.ssh/config
|
||||||
|
|
||||||
RUN echo > config.yml
|
RUN echo > config.yml
|
||||||
VOLUME /opt/jumpserver/data
|
VOLUME /opt/jumpserver/data
|
||||||
|
|
|
@ -1,3 +1,5 @@
|
||||||
|
import uuid
|
||||||
|
|
||||||
from common.exceptions import JMSException
|
from common.exceptions import JMSException
|
||||||
from orgs.models import Organization
|
from orgs.models import Organization
|
||||||
from .. import models
|
from .. import models
|
||||||
|
@ -7,6 +9,8 @@ class ApplicationAttrsSerializerViewMixin:
|
||||||
|
|
||||||
def get_serializer_class(self):
|
def get_serializer_class(self):
|
||||||
serializer_class = super().get_serializer_class()
|
serializer_class = super().get_serializer_class()
|
||||||
|
if getattr(self, 'swagger_fake_view', False):
|
||||||
|
return serializer_class
|
||||||
app_type = self.request.query_params.get('type')
|
app_type = self.request.query_params.get('type')
|
||||||
app_category = self.request.query_params.get('category')
|
app_category = self.request.query_params.get('category')
|
||||||
type_options = list(dict(models.Category.get_all_type_serializer_mapper()).keys())
|
type_options = list(dict(models.Category.get_all_type_serializer_mapper()).keys())
|
||||||
|
@ -38,12 +42,16 @@ class ApplicationAttrsSerializerViewMixin:
|
||||||
if app_type:
|
if app_type:
|
||||||
# action: create / update / list / retrieve / metadata
|
# action: create / update / list / retrieve / metadata
|
||||||
attrs_cls = models.Category.get_type_serializer_cls(app_type)
|
attrs_cls = models.Category.get_type_serializer_cls(app_type)
|
||||||
|
class_name = 'ApplicationDynamicSerializer{}'.format(app_type.title())
|
||||||
elif app_category:
|
elif app_category:
|
||||||
# action: list / retrieve / metadata
|
# action: list / retrieve / metadata
|
||||||
attrs_cls = models.Category.get_category_serializer_cls(app_category)
|
attrs_cls = models.Category.get_category_serializer_cls(app_category)
|
||||||
|
class_name = 'ApplicationDynamicSerializer{}'.format(app_category.title())
|
||||||
else:
|
else:
|
||||||
attrs_cls = models.Category.get_no_password_serializer_cls()
|
attrs_cls = models.Category.get_no_password_serializer_cls()
|
||||||
return type('ApplicationDynamicSerializer', (serializer_class,), {'attrs': attrs_cls()})
|
class_name = 'ApplicationDynamicSerializer'
|
||||||
|
cls = type(class_name, (serializer_class,), {'attrs': attrs_cls()})
|
||||||
|
return cls
|
||||||
|
|
||||||
|
|
||||||
class SerializeApplicationToTreeNodeMixin:
|
class SerializeApplicationToTreeNodeMixin:
|
||||||
|
|
|
@ -115,7 +115,6 @@ class AssetTaskCreateApi(generics.CreateAPIView):
|
||||||
class AssetGatewayListApi(generics.ListAPIView):
|
class AssetGatewayListApi(generics.ListAPIView):
|
||||||
permission_classes = (IsOrgAdminOrAppUser,)
|
permission_classes = (IsOrgAdminOrAppUser,)
|
||||||
serializer_class = serializers.GatewayWithAuthSerializer
|
serializer_class = serializers.GatewayWithAuthSerializer
|
||||||
model = Asset
|
|
||||||
|
|
||||||
def get_queryset(self):
|
def get_queryset(self):
|
||||||
asset_id = self.kwargs.get('pk')
|
asset_id = self.kwargs.get('pk')
|
||||||
|
|
|
@ -82,6 +82,12 @@ class LDAPAuthorizationBackend(LDAPBackend):
|
||||||
|
|
||||||
class LDAPUser(_LDAPUser):
|
class LDAPUser(_LDAPUser):
|
||||||
|
|
||||||
|
def _search_for_user_dn_from_ldap_util(self):
|
||||||
|
from settings.utils import LDAPServerUtil
|
||||||
|
util = LDAPServerUtil()
|
||||||
|
user_dn = util.search_for_user_dn(self._username)
|
||||||
|
return user_dn
|
||||||
|
|
||||||
def _search_for_user_dn(self):
|
def _search_for_user_dn(self):
|
||||||
"""
|
"""
|
||||||
This method was overridden because the AUTH_LDAP_USER_SEARCH
|
This method was overridden because the AUTH_LDAP_USER_SEARCH
|
||||||
|
@ -107,7 +113,10 @@ class LDAPUser(_LDAPUser):
|
||||||
if results is not None and len(results) == 1:
|
if results is not None and len(results) == 1:
|
||||||
(user_dn, self._user_attrs) = next(iter(results))
|
(user_dn, self._user_attrs) = next(iter(results))
|
||||||
else:
|
else:
|
||||||
user_dn = None
|
# 解决直接配置DC域,用户认证失败的问题(库不能从整棵树中搜索)
|
||||||
|
user_dn = self._search_for_user_dn_from_ldap_util()
|
||||||
|
self._user_dn = user_dn
|
||||||
|
self._user_attrs = self._load_user_attrs()
|
||||||
|
|
||||||
return user_dn
|
return user_dn
|
||||||
|
|
||||||
|
|
|
@ -5,6 +5,7 @@ from django.urls import path, include, re_path
|
||||||
from django.conf import settings
|
from django.conf import settings
|
||||||
from django.conf.urls.static import static
|
from django.conf.urls.static import static
|
||||||
from django.conf.urls.i18n import i18n_patterns
|
from django.conf.urls.i18n import i18n_patterns
|
||||||
|
from django.http import HttpResponse
|
||||||
from django.views.i18n import JavaScriptCatalog
|
from django.views.i18n import JavaScriptCatalog
|
||||||
|
|
||||||
from . import views, api
|
from . import views, api
|
||||||
|
|
|
@ -128,6 +128,7 @@ class CommandExecutionSerializer(serializers.ModelSerializer):
|
||||||
'result', 'is_finished', 'log_url', 'date_created',
|
'result', 'is_finished', 'log_url', 'date_created',
|
||||||
'date_finished'
|
'date_finished'
|
||||||
]
|
]
|
||||||
|
ref_name = 'OpsCommandExecution'
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def get_log_url(obj):
|
def get_log_url(obj):
|
||||||
|
|
|
@ -72,6 +72,8 @@ class UserGroupGrantedNodeAssetsApi(ListAPIView):
|
||||||
search_fields = ['hostname', 'ip', 'comment']
|
search_fields = ['hostname', 'ip', 'comment']
|
||||||
|
|
||||||
def get_queryset(self):
|
def get_queryset(self):
|
||||||
|
if getattr(self, 'swagger_fake_view', False):
|
||||||
|
return Asset.objects.none()
|
||||||
user_group_id = self.kwargs.get('pk', '')
|
user_group_id = self.kwargs.get('pk', '')
|
||||||
node_id = self.kwargs.get("node_id")
|
node_id = self.kwargs.get("node_id")
|
||||||
node = Node.objects.get(id=node_id)
|
node = Node.objects.get(id=node_id)
|
||||||
|
|
|
@ -31,6 +31,8 @@ class UserDirectGrantedAssetsApi(ListAPIView):
|
||||||
search_fields = ['hostname', 'ip', 'comment']
|
search_fields = ['hostname', 'ip', 'comment']
|
||||||
|
|
||||||
def get_queryset(self):
|
def get_queryset(self):
|
||||||
|
if getattr(self, 'swagger_fake_view', False):
|
||||||
|
return Asset.objects.none()
|
||||||
user = self.user
|
user = self.user
|
||||||
assets = get_user_direct_granted_assets(user)\
|
assets = get_user_direct_granted_assets(user)\
|
||||||
.prefetch_related('platform')\
|
.prefetch_related('platform')\
|
||||||
|
@ -45,6 +47,8 @@ class UserFavoriteGrantedAssetsApi(ListAPIView):
|
||||||
search_fields = ['hostname', 'ip', 'comment']
|
search_fields = ['hostname', 'ip', 'comment']
|
||||||
|
|
||||||
def get_queryset(self):
|
def get_queryset(self):
|
||||||
|
if getattr(self, 'swagger_fake_view', False):
|
||||||
|
return Asset.objects.none()
|
||||||
user = self.user
|
user = self.user
|
||||||
assets = FavoriteAsset.get_user_favorite_assets(user)\
|
assets = FavoriteAsset.get_user_favorite_assets(user)\
|
||||||
.prefetch_related('platform')\
|
.prefetch_related('platform')\
|
||||||
|
@ -101,6 +105,8 @@ class UserAllGrantedAssetsApi(ForAdminMixin, ListAPIView):
|
||||||
search_fields = ['hostname', 'ip', 'comment']
|
search_fields = ['hostname', 'ip', 'comment']
|
||||||
|
|
||||||
def get_queryset(self):
|
def get_queryset(self):
|
||||||
|
if getattr(self, 'swagger_fake_view', False):
|
||||||
|
return Asset.objects.none()
|
||||||
queryset = get_user_granted_all_assets(self.user)
|
queryset = get_user_granted_all_assets(self.user)
|
||||||
queryset = queryset.prefetch_related('platform')
|
queryset = queryset.prefetch_related('platform')
|
||||||
return queryset.only(*self.only_fields)
|
return queryset.only(*self.only_fields)
|
||||||
|
@ -123,6 +129,8 @@ class UserGrantedNodeAssetsApi(UserNodeGrantStatusDispatchMixin, ListAPIView):
|
||||||
pagination_node: Node
|
pagination_node: Node
|
||||||
|
|
||||||
def get_queryset(self):
|
def get_queryset(self):
|
||||||
|
if getattr(self, 'swagger_fake_view', False):
|
||||||
|
return Asset.objects.none()
|
||||||
node_id = self.kwargs.get("node_id")
|
node_id = self.kwargs.get("node_id")
|
||||||
node = Node.objects.get(id=node_id)
|
node = Node.objects.get(id=node_id)
|
||||||
self.pagination_node = node
|
self.pagination_node = node
|
||||||
|
|
|
@ -15,7 +15,7 @@ __all__ = [
|
||||||
|
|
||||||
class BasePermissionViewSet(OrgBulkModelViewSet):
|
class BasePermissionViewSet(OrgBulkModelViewSet):
|
||||||
custom_filter_fields = [
|
custom_filter_fields = [
|
||||||
'user_id', 'username', 'search', 'system_user_id', 'system_user',
|
'user_id', 'username', 'system_user_id', 'system_user',
|
||||||
'user_group_id', 'user_group'
|
'user_group_id', 'user_group'
|
||||||
]
|
]
|
||||||
permission_classes = (IsOrgAdmin,)
|
permission_classes = (IsOrgAdmin,)
|
||||||
|
|
|
@ -62,6 +62,8 @@ class Action:
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def value_to_choices(cls, value):
|
def value_to_choices(cls, value):
|
||||||
|
if isinstance(value, list):
|
||||||
|
return value
|
||||||
value = int(value)
|
value = int(value)
|
||||||
choices = [cls.NAME_MAP[i] for i, j in cls.DB_CHOICES if value & i == i]
|
choices = [cls.NAME_MAP[i] for i, j in cls.DB_CHOICES if value & i == i]
|
||||||
return choices
|
return choices
|
||||||
|
|
|
@ -16,3 +16,4 @@ class SystemUserSerializer(serializers.ModelSerializer):
|
||||||
'auto_push', 'cmd_filters', 'sudo', 'shell', 'comment',
|
'auto_push', 'cmd_filters', 'sudo', 'shell', 'comment',
|
||||||
'sftp_root', 'date_created', 'created_by'
|
'sftp_root', 'date_created', 'created_by'
|
||||||
]
|
]
|
||||||
|
ref_name = 'PermedSystemUserSerializer'
|
||||||
|
|
|
@ -145,9 +145,22 @@ class LDAPServerUtil(object):
|
||||||
paged_cookie=paged_cookie
|
paged_cookie=paged_cookie
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def distinct_user_entries(user_entries):
|
||||||
|
distinct_user_entries = list()
|
||||||
|
distinct_user_entries_dn = set()
|
||||||
|
for user_entry in user_entries:
|
||||||
|
if user_entry.entry_dn in distinct_user_entries_dn:
|
||||||
|
continue
|
||||||
|
distinct_user_entries_dn.add(user_entry.entry_dn)
|
||||||
|
distinct_user_entries.append(user_entry)
|
||||||
|
return distinct_user_entries
|
||||||
|
|
||||||
@timeit
|
@timeit
|
||||||
def search_user_entries(self):
|
def search_user_entries(self, search_users=None, search_value=None):
|
||||||
logger.info("Search user entries")
|
logger.info("Search user entries")
|
||||||
|
self.search_users = search_users
|
||||||
|
self.search_value = search_value
|
||||||
user_entries = list()
|
user_entries = list()
|
||||||
search_ous = str(self.config.search_ou).split('|')
|
search_ous = str(self.config.search_ou).split('|')
|
||||||
for search_ou in search_ous:
|
for search_ou in search_ous:
|
||||||
|
@ -157,6 +170,7 @@ class LDAPServerUtil(object):
|
||||||
while self.paged_cookie():
|
while self.paged_cookie():
|
||||||
self.search_user_entries_ou(search_ou, self.paged_cookie())
|
self.search_user_entries_ou(search_ou, self.paged_cookie())
|
||||||
user_entries.extend(self.connection.entries)
|
user_entries.extend(self.connection.entries)
|
||||||
|
user_entries = self.distinct_user_entries(user_entries)
|
||||||
return user_entries
|
return user_entries
|
||||||
|
|
||||||
def user_entry_to_dict(self, entry):
|
def user_entry_to_dict(self, entry):
|
||||||
|
@ -180,12 +194,22 @@ class LDAPServerUtil(object):
|
||||||
users.append(user)
|
users.append(user)
|
||||||
return users
|
return users
|
||||||
|
|
||||||
|
@timeit
|
||||||
|
def search_for_user_dn(self, username):
|
||||||
|
user_entries = self.search_user_entries(search_users=[username])
|
||||||
|
if len(user_entries) == 1:
|
||||||
|
user_entry = user_entries[0]
|
||||||
|
user_dn = user_entry.entry_dn
|
||||||
|
else:
|
||||||
|
user_dn = None
|
||||||
|
return user_dn
|
||||||
|
|
||||||
@timeit
|
@timeit
|
||||||
def search(self, search_users=None, search_value=None):
|
def search(self, search_users=None, search_value=None):
|
||||||
logger.info("Search ldap users")
|
logger.info("Search ldap users")
|
||||||
self.search_users = search_users
|
user_entries = self.search_user_entries(
|
||||||
self.search_value = search_value
|
search_users=search_users, search_value=search_value
|
||||||
user_entries = self.search_user_entries()
|
)
|
||||||
users = self.user_entries_to_dict(user_entries)
|
users = self.user_entries_to_dict(user_entries)
|
||||||
return users
|
return users
|
||||||
|
|
||||||
|
|
|
@ -68,3 +68,4 @@ class TaskSerializer(BulkModelSerializer):
|
||||||
fields = '__all__'
|
fields = '__all__'
|
||||||
model = Task
|
model = Task
|
||||||
list_serializer_class = AdaptedBulkListSerializer
|
list_serializer_class = AdaptedBulkListSerializer
|
||||||
|
ref_name = 'TerminalTaskSerializer'
|
||||||
|
|
Loading…
Reference in New Issue