diff --git a/scheduler/main/migrations/0002_schedule_uuid.py b/scheduler/main/migrations/0002_schedule_uuid.py new file mode 100644 index 0000000000000000000000000000000000000000..07048feeb1f12c6f351d2597ee7d67ed326448c7 --- /dev/null +++ b/scheduler/main/migrations/0002_schedule_uuid.py @@ -0,0 +1,19 @@ +# Generated by Django 3.1.6 on 2021-02-22 14:39 + +from django.db import migrations, models +import uuid + + +class Migration(migrations.Migration): + + dependencies = [ + ('main', '0001_initial'), + ] + + operations = [ + migrations.AddField( + model_name='schedule', + name='uuid', + field=models.UUIDField(default=uuid.uuid4, editable=False, unique=True), + ), + ] diff --git a/scheduler/main/models.py b/scheduler/main/models.py index 4a823d74e13013b6d40df55f31e050deb5a25225..dfd15a4ec35ebfb0e9b565f7045f5d518e446fbb 100644 --- a/scheduler/main/models.py +++ b/scheduler/main/models.py @@ -17,6 +17,7 @@ # . import datetime +import uuid from django.db import models from django.utils import formats @@ -24,6 +25,7 @@ from django.utils.translation import gettext_lazy as _ class Schedule(models.Model): + uuid = models.UUIDField(default=uuid.uuid4, unique=True, editable=False) title = models.CharField(_('Title'), max_length=254) def __str__(self): diff --git a/scheduler/main/templates/main/schedule_form.html b/scheduler/main/templates/main/schedule_form.html index 789536f0489ea52b348fbcc9d340d6bee4733f5b..8d436856f1de33f2ab9d7083ab7693e0bf8c1f56 100644 --- a/scheduler/main/templates/main/schedule_form.html +++ b/scheduler/main/templates/main/schedule_form.html @@ -69,7 +69,7 @@
- +
diff --git a/scheduler/main/views.py b/scheduler/main/views.py index 6f59f9b287d0ffbeb8d852d14d405313c43d73bc..be429cac7d0d42f8e457b205a151a90a76b1661c 100644 --- a/scheduler/main/views.py +++ b/scheduler/main/views.py @@ -53,7 +53,7 @@ class ScheduleFormMixin(LoginRequiredMixin): form_class = ScheduleForm def get_success_url(self): - return reverse('schedule-update', args=[self.object.pk]) + return reverse('schedule-update', args=[self.object.uuid]) def form_valid(self, form, *args): messages.success(self.request, _('Data has been saved.')) @@ -65,11 +65,14 @@ class ScheduleCreateView(ScheduleFormMixin, CreateView): class ScheduleUpdateView(ScheduleFormMixin, UpdateView): - pass + slug_field = 'uuid' + slug_url_kwarg = 'uuid' class ScheduleDeleteView(LoginRequiredMixin, DeleteView): model = Schedule + slug_field = 'uuid' + slug_url_kwarg = 'uuid' def get_success_url(self): return reverse('index') @@ -85,7 +88,7 @@ class InvitationUpdateView(UpdateView): return get_object_or_404(Invitation, **self.kwargs) def get_success_url(self): - return reverse('invitation', args=[self.object.schedule.pk, self.object.token]) + return reverse('invitation', args=[self.object.schedule.uuid, self.object.token]) def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) @@ -150,6 +153,9 @@ class InvitationApiView(View): }) def put(self, request, *args, **kwargs): + if 'schedule__uuid' in kwargs: + schedule = get_object_or_404(Schedule, uuid=kwargs.pop('schedule__uuid')) + kwargs['schedule_id'] = schedule.id invitation, _ = Invitation.objects.get_or_create(**kwargs) return HttpResponse(status=204) diff --git a/scheduler/tests.py b/scheduler/tests.py index a5220d33d526b67fcae2c2a99750332fb5ac9298..847d0ccb3a22dc66db84de9ab0a990d13ae77a61 100644 --- a/scheduler/tests.py +++ b/scheduler/tests.py @@ -7,7 +7,7 @@ from .main.models import Schedule from .main.models import Invitation -class TestInvitationApiView(TestCase): +class TestLegacyInvitationApiView(TestCase): def setUp(self): self.client.defaults['HTTP_AUTHORIZATION'] = 'token ' + settings.API_TOKEN @@ -30,3 +30,28 @@ class TestInvitationApiView(TestCase): response = self.client.delete(url) self.assertEqual(response.status_code, 204) self.assertFalse(Invitation.objects.filter(token=invitation.token).exists()) + + +class TestInvitationApiView(TestCase): + def setUp(self): + self.client.defaults['HTTP_AUTHORIZATION'] = 'token ' + settings.API_TOKEN + + def test_get(self): + invitation = baker.make(Invitation) + url = '/api/{}/{}/'.format(invitation.schedule.uuid, invitation.token) + response = self.client.get(url) + self.assertEqual(response.status_code, 200) + + def test_put(self): + schedule = baker.make(Schedule) + url = '/api/{}/{}/'.format(schedule.uuid, 'sometoken') + response = self.client.put(url) + self.assertEqual(response.status_code, 204) + self.assertTrue(Invitation.objects.filter(token='sometoken').exists()) + + def test_delete(self): + invitation = baker.make(Invitation) + url = '/api/{}/{}/'.format(invitation.schedule.uuid, invitation.token) + response = self.client.delete(url) + self.assertEqual(response.status_code, 204) + self.assertFalse(Invitation.objects.filter(token=invitation.token).exists()) diff --git a/scheduler/urls.py b/scheduler/urls.py index da2f6bdb4af9f72fab241df03377f817fb5e3984..38de4f39733ce57b933351f05ecc257ca5568dc0 100644 --- a/scheduler/urls.py +++ b/scheduler/urls.py @@ -35,16 +35,28 @@ from .main.views import ScheduleUpdateView urlpatterns = [ path('', ScheduleListView.as_view(), name='index'), path('new/', ScheduleCreateView.as_view(), name='schedule-create'), - path('/', ScheduleUpdateView.as_view(), name='schedule-update'), - path('/delete/', ScheduleDeleteView.as_view(), name='schedule-delete'), + path('/', ScheduleUpdateView.as_view(), name='schedule-update-legacy'), + path('/', ScheduleUpdateView.as_view(), name='schedule-update'), + path('/delete/', ScheduleDeleteView.as_view(), name='schedule-delete-legacy'), + path('/delete/', ScheduleDeleteView.as_view(), name='schedule-delete'), path( 'invitations///', InvitationUpdateView.as_view(), + name='invitation-legacy', + ), + path( + 'invitations///', + InvitationUpdateView.as_view(), name='invitation', ), path( 'api///', InvitationApiView.as_view(), + name='api-invitation-legacy', + ), + path( + 'api///', + InvitationApiView.as_view(), name='api-invitation', ), path('login/', LoginView.as_view(), name='login'),