From 369baf3ff6b40b7aaa389190fee0b6b928838da0 Mon Sep 17 00:00:00 2001
From: Andreas Ellewsen <ae@uio.no>
Date: Wed, 17 Nov 2021 09:40:43 +0100
Subject: [PATCH] Check more things in ui role endpoint

Start dates can now be blank, check for correct sponsor has been moved
to the more appropriate validate method and we now check that the role
exists before doing anything in the serializer
---
 gregui/api/serializers/role.py | 16 ++++++++++++----
 gregui/api/views/role.py       |  7 +++++--
 2 files changed, 17 insertions(+), 6 deletions(-)

diff --git a/gregui/api/serializers/role.py b/gregui/api/serializers/role.py
index 722c8e8f..0b867f09 100644
--- a/gregui/api/serializers/role.py
+++ b/gregui/api/serializers/role.py
@@ -29,6 +29,12 @@ class RoleSerializerUi(serializers.ModelSerializer):
         ]
 
     def validate_start_date(self, start_date):
+        """Enfore rules for start_date.
+
+        Must be present, can be blank, before today not allowed.
+        """
+        if not start_date:
+            return start_date
         today = datetime.date.today()
         # New start dates cannot be in the past
         if start_date < today:
@@ -54,9 +60,6 @@ class RoleSerializerUi(serializers.ModelSerializer):
             raise ValidationError(
                 "A sponsor can only make changes to roles at units they are sponsors for."
             )
-        # If we are updating an existing roles, we must be the sponsor of the role
-        if self.instance and self.instance.sponsor != sponsor:
-            raise ValidationError("You can only edit your own roles.")
         return unit
 
     def validate(self, attrs):
@@ -69,7 +72,7 @@ class RoleSerializerUi(serializers.ModelSerializer):
             max_days = today + datetime.timedelta(days=attrs["type"].max_days)
         if attrs["end_date"] > max_days:
             raise serializers.ValidationError(
-                f"New end date too far into the future for this type. Must be before {max_days.strftime('%Y-%m-%d')}"
+                f"New end date too far into the future for this type. Must be before {max_days.strftime('%Y-%m-%d')}."
             )
         # Ensure end date is after start date if start date is set
         if self.instance:
@@ -84,6 +87,11 @@ class RoleSerializerUi(serializers.ModelSerializer):
                 raise serializers.ValidationError(
                     "End date cannot be before start date."
                 )
+        # If we are updating an existing roles, we must be the sponsor of the role
+        sponsor = self.context["sponsor"]
+        if self.instance and self.instance.sponsor != sponsor:
+            raise ValidationError("You can only edit your own roles.")
+
         return attrs
 
 
diff --git a/gregui/api/views/role.py b/gregui/api/views/role.py
index 7424b285..f81e83aa 100644
--- a/gregui/api/views/role.py
+++ b/gregui/api/views/role.py
@@ -1,5 +1,5 @@
 from django.db import transaction
-from rest_framework import serializers, status
+from rest_framework import status
 from rest_framework.authentication import BasicAuthentication, SessionAuthentication
 from rest_framework.viewsets import ModelViewSet
 from rest_framework.permissions import IsAuthenticated
@@ -18,7 +18,10 @@ class RoleInfoViewSet(ModelViewSet):
     serializer_class = RoleSerializerUi
 
     def partial_update(self, request, pk):
-        role = Role.objects.get(pk=pk)
+        try:
+            role = Role.objects.get(pk=pk)
+        except Role.DoesNotExist:
+            return Response(status=status.HTTP_400_BAD_REQUEST)
         sponsor = GregUserProfile.objects.get(user=self.request.user).sponsor
         with transaction.atomic():
             serializer = self.serializer_class(
-- 
GitLab