diff --git a/ietf/liaisons/forms.py b/ietf/liaisons/forms.py index cc36fec7a..abb1888e1 100644 --- a/ietf/liaisons/forms.py +++ b/ietf/liaisons/forms.py @@ -247,9 +247,9 @@ class IncomingLiaisonForm(LiaisonForm): def get_post_only(self): from_entity = self.get_from_entity() - if self.person.liaisonmanagers_set.filter(sdo=from_entity.obj): - return True - return False + if is_secretariat(self.user) or self.person.sdoauthorizedindividual_set.filter(sdo=from_entity.obj): + return False + return True def clean(self): if 'send' in self.data.keys() and self.get_post_only(): @@ -271,15 +271,24 @@ class OutgoingLiaisonForm(LiaisonForm): return organization def set_from_field(self): - if is_secretariat(self.user) or is_sdo_liaison_manager(self.person): + if is_secretariat(self.user): self.fields['from_field'].choices = self.hm.get_all_incoming_entities() + elif is_sdo_liaison_manager(self.person): + self.fields['from_field'].choices = self.hm.get_all_incoming_entities() + all_entities = [] + for i in self.hm.get_entities_for_person(self.person): + all_entities += i[1] + if all_entities: + self.fields['from_field'].widget.full_power_on = [i[0] for i in all_entities] + self.fields['from_field'].widget.reduced_to_set = ['sdo_%s' % i.sdo.pk for i in self.person.liaisonmanagers_set.all().distinct()] else: self.fields['from_field'].choices = self.hm.get_entities_for_person(self.person) self.fields['from_field'].widget.submitter = unicode(self.person) self.fieldsets[0] = ('From', ('from_field', 'replyto', 'approved')) def set_organization_field(self): - if is_sdo_liaison_manager(self.person): + # If the user is a liaison manager and is nothing more, reduce the To field to his SDOs + if not self.hm.get_entities_for_person(self.person) and is_sdo_liaison_manager(self.person): sdos = [i.sdo for i in self.person.liaisonmanagers_set.all().distinct()] self.fields['organization'].choices = [('sdo_%s' % i.pk, i.sdo_name) for i in sdos] else: @@ -322,6 +331,24 @@ class OutgoingLiaisonForm(LiaisonForm): self.check_email(value) return value + def clean_organization(self): + to_code = self.cleaned_data.get('organization', None) + from_code = self.cleaned_data.get('from_field', None) + if not to_code or not from_code: + return to_code + all_entities = [] + for i in self.hm.get_entities_for_person(self.person): + all_entities += i[1] + # If the from entity is one in wich the user has full privileges the to entity could be anyone + if from_code in [i[0] for i in all_entities]: + return to_code + sdo_codes = ['sdo_%s' % i.sdo.pk for i in self.person.liaisonmanagers_set.all().distinct()] + if to_code in sdo_codes: + return to_code + entity = self.get_to_entity() + entity_name = entity and entity.name or to_code + raise forms.ValidationError('You are not allowed to send a liaison to: %s' % entity_name) + class EditLiaisonForm(LiaisonForm): diff --git a/ietf/liaisons/utils.py b/ietf/liaisons/utils.py index 6fe070b37..b414d292c 100644 --- a/ietf/liaisons/utils.py +++ b/ietf/liaisons/utils.py @@ -1,7 +1,8 @@ from ietf.idtracker.models import Area, IETFWG from ietf.liaisons.models import SDOs, LiaisonManagers from ietf.liaisons.accounts import (is_ietfchair, is_iabchair, is_iab_executive_director, - get_ietf_chair, get_iab_chair, get_iab_executive_director) + get_ietf_chair, get_iab_chair, get_iab_executive_director, + is_secretariat) IETFCHAIR = {'name': u'The IETF Chair', 'address': u'chair@ietf.org'} IESG = {'name': u'The IESG', 'address': u'iesg@ietf.org'} @@ -194,8 +195,10 @@ class SDOEntity(Entity): return [manager.person] return [] - def post_only(self, person): - return bool(self.obj.liaisonmanagers_set.filter(person=person)) + def post_only(self, person, user): + if is_secretariat(user) or person.sdoauthorizedindividual_set.filter(sdo=self.obj): + return False + return True def full_user_list(self): result = [i.person for i in self.obj.liaisonmanagers_set.all().distinct()] diff --git a/ietf/liaisons/views.py b/ietf/liaisons/views.py index 9f3f70a3f..c299df735 100644 --- a/ietf/liaisons/views.py +++ b/ietf/liaisons/views.py @@ -75,7 +75,7 @@ def get_info(request): [i.email() for i in from_entity.get_from_cc(person=person)], 'poc': [i.email() for i in to_entity.get_poc()], 'needs_approval': from_entity.needs_approval(person=person), - 'post_only': from_entity.post_only(person=person)}) + 'post_only': from_entity.post_only(person=person, user=request.user)}) if is_secretariat(request.user): full_list = [(i.pk, i.email()) for i in from_entity.full_user_list()] full_list.sort(lambda x,y: cmp(x[1], y[1])) diff --git a/ietf/liaisons/widgets.py b/ietf/liaisons/widgets.py index 2a76be6e2..74234d9e7 100644 --- a/ietf/liaisons/widgets.py +++ b/ietf/liaisons/widgets.py @@ -7,6 +7,11 @@ from django.utils.safestring import mark_safe class FromWidget(Select): + def __init__(self, *args, **kwargs): + super(FromWidget, self).__init__(*args, **kwargs) + self.full_power_on = [] + self.reduced_to_set = [] + def render(self, name, value, attrs=None, choices=()): all_choices = list(self.choices) + list(choices) if len(all_choices)!=1 or \ @@ -21,6 +26,13 @@ class FromWidget(Select): text = option[1] base = u'%s' % (value, name, name, text) base += u' (' + self.submitter + u')' + if self.full_power_on: + base += '
' return mark_safe(base) diff --git a/static/js/liaisons.js b/static/js/liaisons.js index f2334877d..59d5a9a09 100644 --- a/static/js/liaisons.js +++ b/static/js/liaisons.js @@ -317,10 +317,33 @@ return false; }; + var checkFrom = function() { + var reduce_options = form.find('.reducedToOptions'); + var to_select = organization; + var from_entity = from.val(); + if (!reduce_options.find('.full_power_on_' + from_entity).length) { + to_select.find('optgroup').eq(1).hide(); + to_select.find('option').each(function() { + if (!reduce_options.find('.reduced_to_set_' + $(this).val()).length) { + $(this).hide(); + } else { + $(this).show(); + } + }); + if (!to_select.find('option:selected').is(':visible')) { + to_select.find('option:selected').removeAttr('selected'); + } + } else { + to_select.find('optgroup').show(); + to_select.find('option').show(); + } + updateInfo(); + }; + var initTriggers = function() { organization.change(updateInfo); organization.change(checkOtherSDO); - from.change(updateInfo); + from.change(checkFrom); reply.keyup(updateFrom); purpose.change(updatePurpose); cancel.click(cancelForm); @@ -330,7 +353,7 @@ var updateOnInit = function() { updateFrom(); - updateInfo(); + checkFrom(); updatePurpose(); checkOtherSDO(); };