From 4f5933ae2049078113c9a7a883578ac9a259ddb6 Mon Sep 17 00:00:00 2001 From: Ryan Cross Date: Thu, 16 Mar 2017 23:10:14 +0000 Subject: [PATCH] Add placeholders and validations to secretariat non-session time input fields. Fixes #2208. Commit ready for merge. - Legacy-Id: 13017 --- ietf/secr/meetings/forms.py | 16 +++++++++++++++- ietf/secr/meetings/tests.py | 19 ++++++++++++++++++- ietf/secr/meetings/views.py | 4 ++-- 3 files changed, 35 insertions(+), 4 deletions(-) diff --git a/ietf/secr/meetings/forms.py b/ietf/secr/meetings/forms.py index 05a0c4c29..c25cdff8d 100644 --- a/ietf/secr/meetings/forms.py +++ b/ietf/secr/meetings/forms.py @@ -22,7 +22,9 @@ SESSION_DAYS = ((2,'Monday'), (4,'Wednesday'), (5,'Thursday'), (6,'Friday')) - + +SESSION_DURATION_RE = re.compile(r'^\d{2}:\d{2}') + #---------------------------------------------------------- # Helper Functions #---------------------------------------------------------- @@ -186,6 +188,13 @@ class TimeSlotForm(forms.Form): duration = ietf.utils.fields.DurationField() name = forms.CharField(help_text='Name that appears on the agenda') + def clean_duration(self): + '''Limit to HH:MM format''' + duration = self.data['duration'] + if not SESSION_DURATION_RE.match(duration): + raise forms.ValidationError('{} value has an invalid format. It must be in HH:MM format'.format(duration)) + return self.cleaned_data['duration'] + class NonSessionForm(TimeSlotForm): short = forms.CharField(max_length=32,label='Short Name',help_text='Enter an abbreviated session name (used for material file names)',required=False) type = forms.ModelChoiceField(queryset=TimeSlotTypeName.objects.filter(used=True).exclude(slug__in=('session',)),empty_label=None) @@ -195,6 +204,11 @@ class NonSessionForm(TimeSlotForm): required=False) show_location = forms.BooleanField(required=False) + def __init__(self,*args,**kwargs): + super(NonSessionForm, self).__init__(*args,**kwargs) + self.fields["time"].widget.attrs["placeholder"] = "HH:MM" + self.fields["duration"].widget.attrs["placeholder"] = "HH:MM" + def clean(self): super(NonSessionForm, self).clean() if any(self.errors): diff --git a/ietf/secr/meetings/tests.py b/ietf/secr/meetings/tests.py index 456022fd7..b0b190719 100644 --- a/ietf/secr/meetings/tests.py +++ b/ietf/secr/meetings/tests.py @@ -238,7 +238,7 @@ class SecrMeetingTestCase(TestCase): response = self.client.post(url, { 'day':'1', 'time':'08:00', - 'duration':'1 0:0:0', + 'duration':'09:00', 'name':'Testing' }) self.assertEqual(response.status_code, 302) @@ -251,6 +251,23 @@ class SecrMeetingTestCase(TestCase): response = self.client.get(url) self.assertEqual(response.status_code, 200) + def test_meetings_nonsession_add_invalid(self): + make_meeting_test_data() + group = Group.objects.get(acronym='secretariat') + url = reverse('ietf.secr.meetings.views.non_session',kwargs={'meeting_id':42,'schedule_name':'test-agenda'}) + self.client.login(username="secretary", password="secretary+password") + response = self.client.post(url, { + 'day':'1', + 'time':'08:00', + 'duration':'10', + 'name':'Testing', + 'short':'test', + 'type':'reg', + 'group':group.pk, + }) + self.assertEqual(response.status_code, 200) + self.assertTrue('invalid format' in response.content) + def test_meetings_select_group(self): make_meeting_test_data() url = reverse('ietf.secr.meetings.views.select_group',kwargs={'meeting_id':42,'schedule_name':'test-agenda'}) diff --git a/ietf/secr/meetings/views.py b/ietf/secr/meetings/views.py index bd2c15a8b..9eeb0bb7b 100644 --- a/ietf/secr/meetings/views.py +++ b/ietf/secr/meetings/views.py @@ -99,7 +99,7 @@ def build_nonsession(meeting,schedule): return None delta = meeting.date - last_meeting.date - system = Person.objects.get(name='(system)') + system = Person.objects.get(name='(System)') secretariat = Group.objects.get(acronym='secretariat') for slot in TimeSlot.objects.filter(meeting=last_meeting,type__in=('break','reg','other','plenary','lead')): @@ -487,7 +487,7 @@ def non_session(request, meeting_id, schedule_name): name=name, short=short, group=group, - requested_by=Person.objects.get(name='(system)'), + requested_by=Person.objects.get(name='(System)'), status_id='sched', type=type, )