from django.db import transaction from django.db.models import Count from django.shortcuts import get_object_or_404 from django.utils.translation import ugettext as _ from rest_framework import status from rest_framework.response import Response from orgs.mixins.api import OrgBulkModelViewSet from orgs.mixins import generics from common.utils import get_logger from ..hands import IsOrgAdmin from ..models import AdminUser, Asset from .. import serializers from ..tasks import test_admin_user_connectivity_manual logger = get_logger(__file__) __all__ = [ 'AdminUserViewSet', 'ReplaceNodesAdminUserApi', 'AdminUserTestConnectiveApi', 'AdminUserAuthApi', 'AdminUserAssetsListView', ] class AdminUserViewSet(OrgBulkModelViewSet): """ Admin user api set, for add,delete,update,list,retrieve resource """ model = AdminUser filterset_fields = ("name", "username") search_fields = filterset_fields serializer_class = serializers.AdminUserSerializer permission_classes = (IsOrgAdmin,) serializer_classes = { 'default': serializers.AdminUserSerializer, 'retrieve': serializers.AdminUserDetailSerializer, } def get_queryset(self): queryset = super().get_queryset() queryset = queryset.annotate(assets_amount=Count('assets')) return queryset def destroy(self, request, *args, **kwargs): instance = self.get_object() has_related_asset = instance.assets.exists() if has_related_asset: data = {'msg': _('Deleted failed, There are related assets')} return Response(data=data, status=status.HTTP_400_BAD_REQUEST) return super().destroy(request, *args, **kwargs) class AdminUserAuthApi(generics.UpdateAPIView): model = AdminUser serializer_class = serializers.AdminUserAuthSerializer permission_classes = (IsOrgAdmin,) class ReplaceNodesAdminUserApi(generics.UpdateAPIView): model = AdminUser serializer_class = serializers.ReplaceNodeAdminUserSerializer permission_classes = (IsOrgAdmin,) def update(self, request, *args, **kwargs): admin_user = self.get_object() serializer = self.serializer_class(data=request.data) if serializer.is_valid(): nodes = serializer.validated_data['nodes'] assets = [] for node in nodes: assets.extend([asset.id for asset in node.get_all_assets()]) with transaction.atomic(): Asset.objects.filter(id__in=assets).update(admin_user=admin_user) return Response({"msg": "ok"}) else: return Response({'error': serializer.errors}, status=400) class AdminUserTestConnectiveApi(generics.RetrieveAPIView): """ Test asset admin user assets_connectivity """ model = AdminUser permission_classes = (IsOrgAdmin,) serializer_class = serializers.TaskIDSerializer def retrieve(self, request, *args, **kwargs): admin_user = self.get_object() task = test_admin_user_connectivity_manual.delay(admin_user) return Response({"task": task.id}) class AdminUserAssetsListView(generics.ListAPIView): permission_classes = (IsOrgAdmin,) serializer_class = serializers.AssetSimpleSerializer filterset_fields = ("hostname", "ip") search_fields = filterset_fields def get_object(self): pk = self.kwargs.get('pk') return get_object_or_404(AdminUser, pk=pk) def get_queryset(self): admin_user = self.get_object() return admin_user.get_related_assets()