From b415d8f35b10fc57a7e23bb7a58eb4db0100a16b Mon Sep 17 00:00:00 2001 From: i701 Date: Sun, 6 Apr 2025 21:38:41 +0500 Subject: [PATCH] Add BlockDeviceSerializer and DeviceBlockAPIView for blocking devices --- devices/serializers.py | 8 ++++++++ devices/urls.py | 5 +++++ devices/views.py | 37 +++++++++++++++++++++++++++++++++++++ 3 files changed, 50 insertions(+) diff --git a/devices/serializers.py b/devices/serializers.py index b153dbc..57f4c2f 100644 --- a/devices/serializers.py +++ b/devices/serializers.py @@ -9,6 +9,14 @@ class CreateDeviceSerializer(serializers.ModelSerializer): fields = ["name", "mac"] +class BlockDeviceSerializer(serializers.ModelSerializer): + blocked = serializers.BooleanField(required=True) + + class Meta: + model = Device + fields = ["blocked"] + + class DeviceSerializer(serializers.ModelSerializer): class Meta: model = Device diff --git a/devices/urls.py b/devices/urls.py index e927ffb..5f282dc 100644 --- a/devices/urls.py +++ b/devices/urls.py @@ -18,6 +18,11 @@ urlpatterns = [ views.DeviceUpdateAPIView.as_view(), name="device-edit", ), + path( + "/block/", + views.DeviceBlockAPIView.as_view(), + name="device-block", + ), path( "/delete/", views.DeviceDestroyAPIView.as_view(), diff --git a/devices/views.py b/devices/views.py index adf7c40..2ca59a0 100644 --- a/devices/views.py +++ b/devices/views.py @@ -6,6 +6,7 @@ from .serializers import ( CreateDeviceSerializer, DeviceSerializer, ReadOnlyDeviceSerializer, + BlockDeviceSerializer, ) from api.mixins import StaffEditorPermissionMixin from .filters import DeviceFilter @@ -70,8 +71,15 @@ class DeviceUpdateAPIView(StaffEditorPermissionMixin, generics.UpdateAPIView): def update(self, request, *args, **kwargs): # Pass 'partial=True' to allow partial updates + user_id = request.user.id + partial = kwargs.pop("partial", True) instance = self.get_object() + if not request.user.is_superuser and instance.user_id != user_id: + return Response( + {"message": "You are not authorized to update this device."}, + status=403, + ) mac = request.data.get("mac", None) if not re.match(r"^([0-9A-Fa-f]{2}([.:-]?)){5}[0-9A-Fa-f]{2}$", mac): return Response({"message": "Invalid mac address"}, status=400) @@ -81,6 +89,35 @@ class DeviceUpdateAPIView(StaffEditorPermissionMixin, generics.UpdateAPIView): return Response(serializer.data) +class DeviceBlockAPIView(StaffEditorPermissionMixin, generics.UpdateAPIView): + queryset = Device.objects.all() + serializer_class = BlockDeviceSerializer + lookup_field = "pk" + + def update(self, request, *args, **kwargs): + # Pass 'partial=True' to allow partial updates + user_id = request.user.id + + partial = kwargs.pop("partial", True) + instance = self.get_object() + if not request.user.is_superuser and instance.user_id != user_id: + return Response( + {"message": "You are not authorized to block this device."}, + status=403, + ) + blocked = request.data.get("blocked", None) + if blocked is None: + return Response({"message": "Blocked field is required."}, status=400) + if not isinstance(blocked, bool): + return Response({"message": "Blocked field must be a boolean."}, status=400) + instance.blocked = blocked + instance.save() + serializer = self.get_serializer(instance, data=request.data, partial=partial) + serializer.is_valid(raise_exception=True) + self.perform_update(serializer) + return Response(serializer.data) + + class DeviceDestroyAPIView(StaffEditorPermissionMixin, generics.DestroyAPIView): queryset = Device.objects.all() serializer_class = DeviceSerializer