From b6623936642843ee43701f2ab11ce2ba4fec8e80 Mon Sep 17 00:00:00 2001 From: Robert Sparks Date: Tue, 2 Aug 2016 14:46:09 +0000 Subject: [PATCH 1/6] refactor columns - Legacy-Id: 11745 --- ietf/templates/meeting/group_proceedings.html | 61 +++++++++++++++++++ ietf/templates/meeting/proceedings.html | 25 +++----- 2 files changed, 71 insertions(+), 15 deletions(-) create mode 100644 ietf/templates/meeting/group_proceedings.html diff --git a/ietf/templates/meeting/group_proceedings.html b/ietf/templates/meeting/group_proceedings.html new file mode 100644 index 000000000..365493c1b --- /dev/null +++ b/ietf/templates/meeting/group_proceedings.html @@ -0,0 +1,61 @@ +{# Copyright The IETF Trust 2015, All Rights Reserved #}{% load origin %}{% origin %} +{% load ietf_filters %} + + + {% comment %} + + + + {% endcomment %} + {% if session.name %} +
{{ session.name }}
+ {% else %} +
{{session.group.acronym}}
+ {% if session.group.state.slug == "bof" %} + {{ session.group.state.slug|upper }} + {% endif %} + {% endif %} + + + {% if session.status_id == 'canceled' %} + Session cancelled + {% else %} + + {% if session.agenda %} + Agenda
+ {% else %} + {% if show_agenda == "True" %} + No agenda
+ {% endif %} + {% endif %} + {% if session.minutes %} + Minutes
+ {% else %} + {% if show_agenda == "True" %} + No minutes
+ {% endif %} + {% endif %} + + + + {% with session.slides as slides %} + {% for slide in slides %} + {{ slide.title|clean_whitespace }} +
+ {% empty %} + No slides + {% endfor %} + {% endwith %} + + + {% with session.all_meeting_drafts as drafts %} + {% for draft in drafts %} + {{ draft.canonical_name }}
+ {% empty %} + No drafts + {% endfor %} + {% endwith %} + + {% endif %} + + diff --git a/ietf/templates/meeting/proceedings.html b/ietf/templates/meeting/proceedings.html index 4eff2d783..d46bcf42e 100644 --- a/ietf/templates/meeting/proceedings.html +++ b/ietf/templates/meeting/proceedings.html @@ -35,8 +35,7 @@ Group - Agenda - Minutes + Artifacts Slides Drafts @@ -44,7 +43,7 @@ {% for session in plenaries %} - {% include "meeting/group_materials.html" %} + {% include "meeting/group_proceedings.html" %} {% endfor %} @@ -58,8 +57,7 @@ Group - Agenda - Minutes + Artifacts Slides Drafts @@ -68,7 +66,7 @@ {% for session in sessions.list|dictsort:"group.acronym" %} {% ifchanged session.group.acronym %} - {% include "meeting/group_materials.html" %} + {% include "meeting/group_proceedings.html" %} {% endifchanged %} {% endfor %} @@ -83,8 +81,7 @@ Group - Agenda - Minutes + Artifacts Slides Drafts @@ -93,7 +90,7 @@ {% for session in training %} {% ifchanged %} - {% include "meeting/group_materials.html" %} + {% include "meeting/group_proceedings.html" %} {% endifchanged %} {% endfor %} @@ -108,8 +105,7 @@ Group - Agenda - Minutes + Artifacts Slides Drafts @@ -118,7 +114,7 @@ {% for session in iab %} {% ifchanged %} - {% include "meeting/group_materials.html" %} + {% include "meeting/group_proceedings.html" %} {% endifchanged %} {% endfor %} @@ -132,8 +128,7 @@ Group - Agenda - Minutes + Artifacts Slides Drafts @@ -142,7 +137,7 @@ {% for session in irtf|dictsort:"group.acronym" %} {% ifchanged %} - {% include "meeting/group_materials.html" %} + {% include "meeting/group_proceedings.html" %} {% endifchanged %} {% endfor %} From 261f97e6c1f2aec5c63ec6c77ca7590252e25992 Mon Sep 17 00:00:00 2001 From: Robert Sparks Date: Tue, 2 Aug 2016 15:31:30 +0000 Subject: [PATCH 2/6] Add a column for recordings. Show the recordings for all sessions for a group. - Legacy-Id: 11746 --- ietf/meeting/models.py | 8 ++++++++ ietf/templates/meeting/group_proceedings.html | 5 +++++ ietf/templates/meeting/proceedings.html | 15 ++++++++++----- 3 files changed, 23 insertions(+), 5 deletions(-) diff --git a/ietf/meeting/models.py b/ietf/meeting/models.py index 6f660d621..164c03fd8 100644 --- a/ietf/meeting/models.py +++ b/ietf/meeting/models.py @@ -1016,6 +1016,14 @@ class Session(models.Model): def drafts(self): return list(self.materials.filter(type='draft')) + def all_meeting_recordings(self): + recordings = [] + sessions = sorted(self.meeting.session_set.filter(group=self.group), + key = lambda x: x.official_timeslotassignment().timeslot.time) + for session in sessions: + recordings.extend(session.recordings()) + return recordings + def all_meeting_drafts(self): drafts = [] for session in self.meeting.session_set.filter(group=self.group): diff --git a/ietf/templates/meeting/group_proceedings.html b/ietf/templates/meeting/group_proceedings.html index 365493c1b..75ff60f8f 100644 --- a/ietf/templates/meeting/group_proceedings.html +++ b/ietf/templates/meeting/group_proceedings.html @@ -37,6 +37,11 @@ {% endif %} + + {% for rec in session.all_meeting_recordings %} + {{rec.title}}
+ {% endfor %} + {% with session.slides as slides %} {% for slide in slides %} diff --git a/ietf/templates/meeting/proceedings.html b/ietf/templates/meeting/proceedings.html index d46bcf42e..834c1f0fa 100644 --- a/ietf/templates/meeting/proceedings.html +++ b/ietf/templates/meeting/proceedings.html @@ -36,7 +36,8 @@ Group Artifacts - Slides + Recordings + Slides Drafts @@ -58,7 +59,8 @@ Group Artifacts - Slides + Recordings + Slides Drafts @@ -82,7 +84,8 @@ Group Artifacts - Slides + Recordings + Slides Drafts @@ -106,7 +109,8 @@ Group Artifacts - Slides + Recordings + Slides Drafts @@ -129,7 +133,8 @@ Group Artifacts - Slides + Recordings + Slides Drafts From a34dc40170685bb2f2e16bc16b30ac964163ecd9 Mon Sep 17 00:00:00 2001 From: Robert Sparks Date: Tue, 2 Aug 2016 20:30:40 +0000 Subject: [PATCH 3/6] Migration to create documents and sessionpresentations for ietf95 and 96 bluesheets. Add bluesheets to proceedings. - Legacy-Id: 11747 --- ..._reconstruct_bluesheet_docs_95through96.py | 69 +++++++++++++++++++ ietf/meeting/models.py | 11 +++ ietf/templates/meeting/group_proceedings.html | 9 +++ 3 files changed, 89 insertions(+) create mode 100644 ietf/meeting/migrations/0029_reconstruct_bluesheet_docs_95through96.py diff --git a/ietf/meeting/migrations/0029_reconstruct_bluesheet_docs_95through96.py b/ietf/meeting/migrations/0029_reconstruct_bluesheet_docs_95through96.py new file mode 100644 index 000000000..5e3b662a3 --- /dev/null +++ b/ietf/meeting/migrations/0029_reconstruct_bluesheet_docs_95through96.py @@ -0,0 +1,69 @@ +# -*- coding: utf-8 -*- +from __future__ import unicode_literals + +import os + +from django.db import migrations +from django.conf import settings + + +def official_time(session): + return session.timeslotassignments.filter(schedule=session.meeting.agenda).first() + +def forward(apps, schema_editor): + Document = apps.get_model('doc','Document') + State = apps.get_model('doc','State') + Group = apps.get_model('group','Group') + Meeting = apps.get_model('meeting', 'Meeting') + + active = State.objects.get(type_id='bluesheets',slug='active') + + for num in [95, 96]: + mtg = Meeting.objects.get(number=num) + bs_path = '%s/bluesheets/'% os.path.join(settings.AGENDA_PATH,mtg.number) + bs_files = os.listdir(bs_path) + bs_acronyms = set([x[14:-7] for x in bs_files]) + group_acronyms = set([x.group.acronym for x in mtg.session_set.all() if official_time(x) and x.group.type_id in ['wg','rg','ag'] and not x.agenda_note.lower().startswith('cancel')]) + + if bs_acronyms-group_acronyms: + print "Warning IETF%s : groups that have bluesheets but did not appear to meet: %s"%(num,list(bs_acronyms-group_acronyms)) + if group_acronyms-bs_acronyms: + print "Warning IETF%s : groups that appeared to meet but have no bluesheets: %s"%(num,list(group_acronyms-bs_acronyms)) + + for acronym in group_acronyms & bs_acronyms: + group = Group.objects.get(acronym=acronym) + bs = sorted([x for x in bs_files if '-%s-'%acronym in x]) + bs_count = len(bs) + sess = sorted([ x for x in mtg.session_set.filter(group__acronym=acronym) if not x.agenda_note.lower().startswith('cancel')], + key = lambda x: official_time(x).timeslot.time) + sess_count = len(sess) + if bs_count != sess_count: + print "Warning IETF%s: %s : different number of bluesheets (%d) than sessions (%d)"%(num,acronym,bs_count,sess_count) + numdocs = min(bs_count,sess_count) + for n in range(numdocs): + doc = Document.objects.create( + name=bs[n][:-4], + type_id='bluesheets', + title='Bluesheets IETF%d : %s : %s ' % (num,acronym,official_time(sess[n]).timeslot.time.strftime('%a %H:%M')), + group=group, + rev='00', + external_url=bs[n], + ) + doc.states.add(active) + sess[n].sessionpresentation_set.create(document=doc,rev='00') + +def reverse(apps, schema_editor): + Document = apps.get_model('doc','Document') + Document.objects.filter(type_id='bluesheets',sessionpresentation__session__meeting__number_in=[95,96]).exclude(group__acronym='openpgp').delete() + +class Migration(migrations.Migration): + + dependencies = [ + ('meeting', '0028_add_audio_stream_data'), + ('doc', '0012_auto_20160207_0537'), + ('group','0008_auto_20160505_0523'), + ] + + operations = [ + migrations.RunPython(forward,reverse) + ] diff --git a/ietf/meeting/models.py b/ietf/meeting/models.py index 164c03fd8..6b1cf57b1 100644 --- a/ietf/meeting/models.py +++ b/ietf/meeting/models.py @@ -1008,6 +1008,9 @@ class Session(models.Model): def recordings(self): return list(self.get_material("recording", only_one=False)) + def bluesheets(self): + return list(self.get_material("bluesheets", only_one=False)) + def slides(self): if not hasattr(self, "_slides_cache"): self._slides_cache = list(self.get_material("slides", only_one=False)) @@ -1024,6 +1027,14 @@ class Session(models.Model): recordings.extend(session.recordings()) return recordings + def all_meeting_bluesheets(self): + bluesheets = [] + sessions = sorted(self.meeting.session_set.filter(group=self.group), + key = lambda x: x.official_timeslotassignment().timeslot.time) + for session in sessions: + bluesheets.extend(session.bluesheets()) + return bluesheets + def all_meeting_drafts(self): drafts = [] for session in self.meeting.session_set.filter(group=self.group): diff --git a/ietf/templates/meeting/group_proceedings.html b/ietf/templates/meeting/group_proceedings.html index 75ff60f8f..c4f8fb366 100644 --- a/ietf/templates/meeting/group_proceedings.html +++ b/ietf/templates/meeting/group_proceedings.html @@ -35,6 +35,15 @@ No minutes
{% endif %} {% endif %} + {% if session.all_meeting_bluesheets %} + {% if session.all_meeting_bluesheets|length == 1 %} + Bluesheets
+ {% else %} + {% for bs in session.all_meeting_bluesheets %} + Bluesheets {{bs.sessionpresentation_set.first.session.official_timeslotassignment.timeslot.time|date:"D G:i"}}
+ {% endfor %} + {% endif %} + {% endif %} From be0ac54535975c64c374c34c574ece64bbdcea47 Mon Sep 17 00:00:00 2001 From: Robert Sparks Date: Wed, 3 Aug 2016 17:35:55 +0000 Subject: [PATCH 4/6] Fixed an incorrect bluesheet href - Legacy-Id: 11754 --- ietf/templates/meeting/group_proceedings.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ietf/templates/meeting/group_proceedings.html b/ietf/templates/meeting/group_proceedings.html index c4f8fb366..25cebdf13 100644 --- a/ietf/templates/meeting/group_proceedings.html +++ b/ietf/templates/meeting/group_proceedings.html @@ -37,7 +37,7 @@ {% endif %} {% if session.all_meeting_bluesheets %} {% if session.all_meeting_bluesheets|length == 1 %} - Bluesheets
+ Bluesheets
{% else %} {% for bs in session.all_meeting_bluesheets %} Bluesheets {{bs.sessionpresentation_set.first.session.official_timeslotassignment.timeslot.time|date:"D G:i"}}
From 2ff54a963bdb1f88f8569ce3b262d96eca0d4c1e Mon Sep 17 00:00:00 2001 From: Robert Sparks Date: Wed, 3 Aug 2016 18:19:39 +0000 Subject: [PATCH 5/6] refactored all_meeting_ functions on session. Improved (with a hack) how recordings are displayed. - Legacy-Id: 11755 --- ietf/meeting/models.py | 13 ++++++++----- ietf/meeting/templatetags/proceedings_filters.py | 14 ++++++++++++++ ietf/templates/meeting/group_proceedings.html | 13 ++++++++++--- 3 files changed, 32 insertions(+), 8 deletions(-) create mode 100644 ietf/meeting/templatetags/proceedings_filters.py diff --git a/ietf/meeting/models.py b/ietf/meeting/models.py index 6b1cf57b1..d34f48a25 100644 --- a/ietf/meeting/models.py +++ b/ietf/meeting/models.py @@ -1019,25 +1019,28 @@ class Session(models.Model): def drafts(self): return list(self.materials.filter(type='draft')) + def all_meeting_sessions_for_group(self): + sessions = [s for s in self.meeting.session_set.filter(group=self.group,type=self.type) if s.official_timeslotassignment()] + return sorted(sessions, key = lambda x: x.official_timeslotassignment().timeslot.time) + def all_meeting_recordings(self): recordings = [] - sessions = sorted(self.meeting.session_set.filter(group=self.group), - key = lambda x: x.official_timeslotassignment().timeslot.time) + sessions = self.all_meeting_sessions_for_group() for session in sessions: recordings.extend(session.recordings()) return recordings def all_meeting_bluesheets(self): bluesheets = [] - sessions = sorted(self.meeting.session_set.filter(group=self.group), - key = lambda x: x.official_timeslotassignment().timeslot.time) + sessions = self.all_meeting_sessions_for_group() for session in sessions: bluesheets.extend(session.bluesheets()) return bluesheets def all_meeting_drafts(self): drafts = [] - for session in self.meeting.session_set.filter(group=self.group): + sessions = self.all_meeting_sessions_for_group() + for session in sessions: drafts.extend(session.drafts()) return drafts diff --git a/ietf/meeting/templatetags/proceedings_filters.py b/ietf/meeting/templatetags/proceedings_filters.py new file mode 100644 index 000000000..4f6bac5f0 --- /dev/null +++ b/ietf/meeting/templatetags/proceedings_filters.py @@ -0,0 +1,14 @@ +from django import template + +register = template.Library() + +@register.filter +def hack_recording_title(recording,add_timestamp=False): + + if recording.title.startswith('Audio recording for') or recording.title.startswith('Video recording for'): + hacked_title = recording.title[:15] + if add_timestamp: + hacked_title += ' '+recording.sessionpresentation_set.first().session.official_timeslotassignment().timeslot.time.strftime("%a %H:%M") + return hacked_title + else: + return recording.title diff --git a/ietf/templates/meeting/group_proceedings.html b/ietf/templates/meeting/group_proceedings.html index 25cebdf13..386a2be1d 100644 --- a/ietf/templates/meeting/group_proceedings.html +++ b/ietf/templates/meeting/group_proceedings.html @@ -1,5 +1,6 @@ {# Copyright The IETF Trust 2015, All Rights Reserved #}{% load origin %}{% origin %} {% load ietf_filters %} +{% load proceedings_filters %} {% comment %} @@ -47,9 +48,15 @@ - {% for rec in session.all_meeting_recordings %} - {{rec.title}}
- {% endfor %} + {% if session.all_meeting_sessions_for_group|length == 1 %} + {% for rec in session.all_meeting_recordings %} + {{rec|hack_recording_title:False}}
+ {% endfor %} + {% else %} + {% for rec in session.all_meeting_recordings %} + {{rec|hack_recording_title:True}}
+ {% endfor %} + {% endif %} {% with session.slides as slides %} From 56c232ec1dfd9c8943cc1b81066f780f5e5cf759 Mon Sep 17 00:00:00 2001 From: Robert Sparks Date: Thu, 4 Aug 2016 21:08:56 +0000 Subject: [PATCH 6/6] Add guards against very old meetings. For more modern, past, meetings, add a warning that these are not the official proceedings and provide a link to the official proceedings. - Legacy-Id: 11757 --- ietf/meeting/views.py | 4 ++++ ietf/templates/meeting/proceedings.html | 5 +++++ 2 files changed, 9 insertions(+) diff --git a/ietf/meeting/views.py b/ietf/meeting/views.py index 7403790ef..cd7cdfba1 100644 --- a/ietf/meeting/views.py +++ b/ietf/meeting/views.py @@ -1446,6 +1446,10 @@ def floor_plan(request, num=None, floor=None, ): def proceedings(request, num=None): meeting = get_meeting(num) + + if meeting.number <= 64 or not meeting.agenda.assignments.exists(): + return HttpResponseRedirect( 'https://www.ietf.org/proceedings/%s' % num ) + begin_date = meeting.get_submission_start_date() cut_off_date = meeting.get_submission_cut_off_date() cor_cut_off_date = meeting.get_submission_correction_date() diff --git a/ietf/templates/meeting/proceedings.html b/ietf/templates/meeting/proceedings.html index 834c1f0fa..3676741f5 100644 --- a/ietf/templates/meeting/proceedings.html +++ b/ietf/templates/meeting/proceedings.html @@ -22,6 +22,11 @@

This page is under construction

+ {% if meeting_num|add:0 <= 96 %} +

+ These are not the official proceedings for IETF{{meeting_num}}. This page shows what would be generated by the new automatic proceedings generator for that meeting. The official proceedings are located at https://www.ietf.org/proceedings/{{meeting_num}} +

+ {% endif %} {# cache for 15 minutes, as long as there's no proceedings activity. takes 4-8 seconds to generate. #} {% load cache %}