parent
439a3b16c7
commit
0ccbe9144f
|
@ -12,13 +12,14 @@ from django.utils.html import format_html
|
|||
from django.utils.encoding import force_text
|
||||
from django.utils.safestring import mark_safe
|
||||
|
||||
|
||||
from ietf.name.models import DocRelationshipName
|
||||
from ietf.liaisons.accounts import (can_add_outgoing_liaison, can_add_incoming_liaison,
|
||||
get_person_for_user, is_secretariat, is_sdo_liaison_manager)
|
||||
from ietf.liaisons.utils import IETFHM
|
||||
from ietf.liaisons.widgets import (FromWidget, ReadOnlyWidget, ButtonWidget,
|
||||
ShowAttachmentsWidget, RelatedLiaisonWidget)
|
||||
from ietf.liaisons.models import LiaisonStatement, LiaisonStatementPurposeName, LiaisonStatementEvent
|
||||
from ietf.liaisons.models import (LiaisonStatement, LiaisonStatementPurposeName, LiaisonStatementEvent,
|
||||
RelatedLiaisonStatement)
|
||||
from ietf.group.models import Group, Role
|
||||
from ietf.person.models import Person, Email
|
||||
from ietf.doc.models import Document
|
||||
|
@ -45,7 +46,7 @@ class LiaisonForm(forms.Form):
|
|||
require=['id_attach_title', 'id_attach_file'],
|
||||
required_label='title and file'),
|
||||
required=False)
|
||||
related_to = forms.ModelChoiceField(LiaisonStatement.objects.all(), label=u'Related Liaison', widget=RelatedLiaisonWidget, required=False)
|
||||
related_to = forms.ModelMultipleChoiceField(LiaisonStatement.objects.all(), label=u'Related Liaison', widget=RelatedLiaisonWidget, required=False)
|
||||
|
||||
fieldsets = [('From', ('from_field', 'response_contacts')),
|
||||
('To', ('organization', 'to_poc')),
|
||||
|
@ -162,6 +163,10 @@ class LiaisonForm(forms.Form):
|
|||
except UnicodeEncodeError as e:
|
||||
raise forms.ValidationError('Invalid email address: %s (check character %d)' % (addr,e.start))
|
||||
|
||||
def clean_related_to(self):
|
||||
related_list = self.data.getlist('related_to')
|
||||
return [i for i in related_list if i]
|
||||
|
||||
def clean_technical_contact(self):
|
||||
value = self.cleaned_data.get('technical_contact', None)
|
||||
self.check_email(value)
|
||||
|
@ -218,21 +223,16 @@ class LiaisonForm(forms.Form):
|
|||
l.purpose = LiaisonStatementPurposeName.objects.get(order=self.cleaned_data["purpose"])
|
||||
l.body = self.cleaned_data["body"].strip()
|
||||
l.deadline = self.cleaned_data["deadline_date"]
|
||||
l.related_to = self.cleaned_data["related_to"]
|
||||
l.response_contacts = self.cleaned_data["response_contacts"]
|
||||
l.technical_contact = self.cleaned_data["technical_contact"]
|
||||
|
||||
now = datetime.datetime.now()
|
||||
|
||||
l.modified = now
|
||||
l.submitted = datetime.datetime.combine(self.cleaned_data["submitted_date"], now.time())
|
||||
if not l.approved:
|
||||
l.approved = now
|
||||
|
||||
self.save_extra_fields(l)
|
||||
|
||||
l.save() # we have to save here to make sure we get an id for the attachments
|
||||
self.save_attachments(l)
|
||||
self.save_related_liaisons(l)
|
||||
|
||||
return l
|
||||
|
||||
|
@ -278,6 +278,16 @@ class LiaisonForm(forms.Form):
|
|||
attach_file.write(attached_file.read())
|
||||
attach_file.close()
|
||||
|
||||
def save_related_liaisons(self, instance):
|
||||
rel = DocRelationshipName.objects.get(slug='refold')
|
||||
for i in self.cleaned_data.get('related_to', []):
|
||||
try:
|
||||
instance.source_of_set.get_or_create(
|
||||
target=LiaisonStatement.objects.get(id=i),
|
||||
relationship=rel)
|
||||
except LiaisonStatement.DoesNotExist:
|
||||
continue
|
||||
|
||||
def clean_title(self):
|
||||
title = self.cleaned_data.get('title', None)
|
||||
if self.instance and self.instance.pk:
|
||||
|
@ -389,10 +399,10 @@ class OutgoingLiaisonForm(LiaisonForm):
|
|||
super(OutgoingLiaisonForm, self).save_extra_fields(liaison)
|
||||
from_entity = self.get_from_entity()
|
||||
needs_approval = from_entity.needs_approval(self.person)
|
||||
if not needs_approval or self.cleaned_data.get('approved', False):
|
||||
liaison.approved = datetime.datetime.now()
|
||||
else:
|
||||
liaison.approved = None
|
||||
#if not needs_approval or self.cleaned_data.get('approved', False):
|
||||
#liaison.approved = datetime.datetime.now()
|
||||
#else:
|
||||
#liaison.approved = None
|
||||
|
||||
def clean_to_poc(self):
|
||||
value = self.cleaned_data.get('to_poc', None)
|
||||
|
|
|
@ -39,12 +39,12 @@ class LiaisonStatement(models.Model):
|
|||
state = models.ForeignKey(LiaisonStatementState, default='pending')
|
||||
|
||||
def name(self):
|
||||
if self.from_group:
|
||||
frm = self.from_group.acronym or self.from_group.name
|
||||
if self.from_groups.count():
|
||||
frm = ', '.join([i.acronym or i.name for i in self.from_groups.all()])
|
||||
else:
|
||||
frm = self.from_name
|
||||
if self.to_group:
|
||||
to = self.to_group.acronym or self.to_group.name
|
||||
if self.to_groups.count():
|
||||
to = ', '.join([i.acronym or i.name for i in self.to_groups.all()])
|
||||
else:
|
||||
to = self.to_name
|
||||
return slugify("liaison" + " " + self.submitted.strftime("%Y-%m-%d") + " " + frm[:50] + " " + to[:50] + " " + self.title[:115])
|
||||
|
|
|
@ -119,12 +119,10 @@ def liaison_list(request):
|
|||
}, context_instance=RequestContext(request))
|
||||
|
||||
def ajax_liaison_list(request):
|
||||
sort, order_by = normalize_sort(request)
|
||||
liaisons = LiaisonStatement.objects.exclude(approved=None).order_by(order_by)
|
||||
liaisons = SearchLiaisonForm().get_results()
|
||||
|
||||
return render_to_response('liaisons/liaison_table.html', {
|
||||
"liaisons": liaisons,
|
||||
"sort": sort,
|
||||
}, context_instance=RequestContext(request))
|
||||
|
||||
@can_submit_liaison_required
|
||||
|
@ -147,8 +145,13 @@ def liaison_approval_detail(request, object_id):
|
|||
send_liaison_by_email(request, liaison)
|
||||
return redirect('liaison_list')
|
||||
|
||||
relations_by = [i.target for i in liaison.source_of_set.filter(target__state__slug='approved')]
|
||||
relations_to = [i.source for i in liaison.target_of_set.filter(source__state__slug='approved')]
|
||||
|
||||
return render_to_response('liaisons/approval_detail.html', {
|
||||
"liaison": liaison,
|
||||
"relations_to": relations_to,
|
||||
"relations_by": relations_by,
|
||||
"is_approving": True,
|
||||
}, context_instance=RequestContext(request))
|
||||
|
||||
|
@ -201,13 +204,15 @@ def liaison_detail(request, object_id):
|
|||
liaison.save()
|
||||
can_take_care = False
|
||||
|
||||
relations = liaison.source_of_set.filter(target__state__slug='approved')
|
||||
relations_by = [i.target for i in liaison.source_of_set.filter(target__state__slug='approved')]
|
||||
relations_to = [i.source for i in liaison.target_of_set.filter(source__state__slug='approved')]
|
||||
|
||||
return render_to_response("liaisons/detail.html", {
|
||||
"liaison": liaison,
|
||||
"can_edit": can_edit,
|
||||
"can_take_care": can_take_care,
|
||||
"relations": relations,
|
||||
"relations_to": relations_to,
|
||||
"relations_by": relations_by,
|
||||
}, context_instance=RequestContext(request))
|
||||
|
||||
def liaison_edit(request, object_id):
|
||||
|
|
|
@ -84,14 +84,13 @@ class ShowAttachmentsWidget(Widget):
|
|||
|
||||
class RelatedLiaisonWidget(TextInput):
|
||||
|
||||
def value_from_datadict(self, data, files, name):
|
||||
return [i for i in data.getlist(name) if i]
|
||||
|
||||
def render(self, name, value, attrs=None):
|
||||
if not value:
|
||||
value = ''
|
||||
title = ''
|
||||
noliaison = 'inline'
|
||||
deselect = 'none'
|
||||
else:
|
||||
liaison = LiaisonStatement.objects.get(pk=value)
|
||||
html = u''
|
||||
for liaison_id in value:
|
||||
liaison = LiaisonStatement.objects.get(pk=liaison_id)
|
||||
title = liaison.title
|
||||
if not title:
|
||||
attachments = liaison.attachments.all()
|
||||
|
@ -101,11 +100,21 @@ class RelatedLiaisonWidget(TextInput):
|
|||
title = 'Liaison #%s' % liaison.pk
|
||||
noliaison = 'none'
|
||||
deselect = 'inline'
|
||||
html = u'<span class="noRelated" style="display: %s;">No liaison selected</span>' % conditional_escape(noliaison)
|
||||
html += u'<span class="relatedLiaisonWidgetTitle">%s</span>' % conditional_escape(title)
|
||||
html += u'<input type="hidden" name="%s" class="relatedLiaisonWidgetValue" value="%s" /> ' % (conditional_escape(name), conditional_escape(value))
|
||||
html += u'<div>'
|
||||
html += u'<span class="noRelated" style="display: %s;"></span>' % conditional_escape(noliaison)
|
||||
html += u'<span class="relatedLiaisonWidgetTitle">%s</span>' % conditional_escape(title)
|
||||
html += u'<input type="hidden" name="%s" class="relatedLiaisonWidgetValue" value="%s" /> ' % (conditional_escape(name), conditional_escape(liaison_id))
|
||||
html += u'<span style="display: none;" class="listURL">%s</span> ' % urlreverse('ajax_liaison_list')
|
||||
html += u'<div style="display: none;" class="relatedLiaisonWidgetDialog" id="related-dialog" title="Select a liaison statement"></div> '
|
||||
html += '<input type="button" style="display: %s;" class="id_no_%s" id="id_no_%s" value="Deselect liaison statement" />' % (conditional_escape(deselect), conditional_escape(name), conditional_escape(name))
|
||||
html += u'</div>'
|
||||
html += u'<div>'
|
||||
html += u'<span class="noRelated" style="display: inline;"></span>'
|
||||
html += u'<span class="relatedLiaisonWidgetTitle"></span>'
|
||||
html += u'<input type="hidden" name="%s" class="relatedLiaisonWidgetValue" value="" /> ' % conditional_escape(name)
|
||||
html += u'<span style="display: none;" class="listURL">%s</span> ' % urlreverse('ajax_liaison_list')
|
||||
html += u'<div style="display: none;" class="relatedLiaisonWidgetDialog" id="related-dialog" title="Select a liaison"></div> '
|
||||
html += '<input type="button" id="id_%s" value="Select liaison" /> ' % conditional_escape(name)
|
||||
html += '<input type="button" style="display: %s;" id="id_no_%s" value="Deselect liaison" />' % (conditional_escape(deselect), conditional_escape(name))
|
||||
html += u'<div style="display: none;" class="relatedLiaisonWidgetDialog" id="related-dialog" title="Select a liaison statement"></div> '
|
||||
html += '<input type="button" class="id_%s" id="id_%s" value="Select liaison statement" /> ' % (conditional_escape(name), conditional_escape(name))
|
||||
html += '<input type="button" style="display: none;" class="id_no_%s" id="id_no_%s" value="Deselect liaison statement" />' % (conditional_escape(name), conditional_escape(name))
|
||||
html += u'</div>'
|
||||
return mark_safe(html)
|
||||
|
|
|
@ -21,37 +21,47 @@
|
|||
<tr>
|
||||
<td style="width:18ex;">Submission Date:</td>
|
||||
<td>{{ liaison.submitted|date:"Y-m-d" }}</td></tr>
|
||||
{% if liaison.from_contact %}<tr>
|
||||
<td>Sender:</td>
|
||||
<td>
|
||||
<a href="mailto:{{ liaison.from_contact.address }}">{{ liaison.from_contact.person }}</a>
|
||||
</td>
|
||||
</tr>{% endif %}
|
||||
<tr>
|
||||
<td>From:</td>
|
||||
<td>{{ liaison.from_name }}
|
||||
{% if liaison.from_contact %}(<a href="mailto:{{ liaison.from_contact.address }}">{{ liaison.from_contact.person }}</a>){% endif %}
|
||||
<td>
|
||||
{% for group in liaison.from_groups.all %}
|
||||
{{ group.name }}
|
||||
{% empty %}
|
||||
{{ liaison.from_name }}
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>To:</td>
|
||||
<td>
|
||||
{% if liaison.from_contact %}
|
||||
{{ liaison.to_name }} ({{ liaison.to_contact|parse_email_list }})
|
||||
{% else %}
|
||||
{{ liaison.to_name|urlize }}
|
||||
{% endif %}
|
||||
{% for group in liaison.to_groups.all %}
|
||||
{{ group.name }}
|
||||
{% empty %}
|
||||
{{ liaison.to_name }}
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
{% if liaison.from_contact %}
|
||||
<tr>
|
||||
<td>Cc:</td><td>{{ liaison.cc|parse_email_list|make_one_per_line|safe|linebreaksbr }}</td>
|
||||
<td>Cc:</td><td>{{ liaison.cc_contacts|parse_email_list|make_one_per_line|safe|linebreaksbr }}</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>Response Contact:</td>
|
||||
<td>{{ liaison.response_contact|parse_email_list|make_one_per_line|safe|linebreaksbr }}</td>
|
||||
<td>{{ liaison.response_contacts|parse_email_list|make_one_per_line|safe|linebreaksbr }}</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>Technical Contact:</td>
|
||||
<td>{{ liaison.technical_contact|parse_email_list|make_one_per_line|safe|linebreaksbr }}</td>
|
||||
<td>{{ liaison.technical_contacts|parse_email_list|make_one_per_line|safe|linebreaksbr }}</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
|
@ -74,11 +84,22 @@
|
|||
{% endif %}
|
||||
{% endif %}
|
||||
|
||||
{% if relations %}
|
||||
{% if relations_by %}
|
||||
<tr>
|
||||
<td>Liaisons referred by this one:</td>
|
||||
<td>
|
||||
{% for rel in relations_by %}
|
||||
<a href="{% url "liaison_detail" rel.pk %}">{% if rel.title %}{{ rel.title }}{% else %}Liaison #{{ rel.pk }}{% endif %}</a><br />
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
|
||||
{% if relations_to %}
|
||||
<tr>
|
||||
<td>Liaisons referring to this one:</td>
|
||||
<td>
|
||||
{% for rel in relations %}
|
||||
{% for rel in relations_to %}
|
||||
<a href="{% url "liaison_detail" rel.pk %}">{% if rel.title %}{{ rel.title }}{% else %}Liaison #{{ rel.pk }}{% endif %}</a><br />
|
||||
{% endfor %}
|
||||
</td>
|
||||
|
|
|
@ -30,5 +30,27 @@ This page depends on Javascript being enabled to work properly. Please enable Ja
|
|||
|
||||
{% block js %}
|
||||
<script type="text/javascript" src="/js/jquery-ui-1.9.0.custom/minified/jquery-ui.custom.min.js"></script>
|
||||
<script type="text/javascript" src="/js/jquery.tablesorter.min.js"></script>
|
||||
<script type="text/javascript" src="/js/liaisons.js"></script>
|
||||
<script type="text/javascript">
|
||||
$(document).ready(function()
|
||||
{
|
||||
var widgetIETF = {css: ["evenrow", "oddrow"]};
|
||||
$.tablesorter.addWidget({
|
||||
id: "ietf",
|
||||
format: function(table) {
|
||||
var $tr, row = -1, odd;
|
||||
$("tr:visible", table.tBodies[0]).each(function (i) {
|
||||
$tr = $(this);
|
||||
if (!$tr.hasClass(table.config.cssChildRow)) row++;
|
||||
odd = (row % 2 == 0);
|
||||
$tr.removeClass(
|
||||
widgetIETF.css[odd ? 0 : 1]).addClass(
|
||||
widgetIETF.css[odd ? 1 : 0])
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
);
|
||||
</script>
|
||||
{% endblock %}
|
||||
|
|
|
@ -138,10 +138,10 @@ jQuery(function () {
|
|||
var cancel = form.find('#id_cancel');
|
||||
var cancel_dialog = form.find('#cancel-dialog');
|
||||
var config = {};
|
||||
var related_trigger = form.find('#id_related_to');
|
||||
var related_trigger = form.find('.id_related_to');
|
||||
var related_url = form.find('#id_related_to').parent().find('.listURL').text();
|
||||
var related_dialog = form.find('#related-dialog');
|
||||
var unrelate_trigger = form.find('#id_no_related_to');
|
||||
var unrelate_trigger = form.find('.id_no_related_to');
|
||||
|
||||
var readConfig = function() {
|
||||
var confcontainer = form.find('.formconfig');
|
||||
|
@ -283,20 +283,22 @@ jQuery(function () {
|
|||
var link = jQuery(this).text();;
|
||||
var pk = jQuery(this).nextAll('.liaisonPK').text();
|
||||
var widget = related_trigger.parent();
|
||||
widget.find('.relatedLiaisonWidgetTitle').text(link);
|
||||
widget.find('.relatedLiaisonWidgetValue').val(pk);
|
||||
widget.find('.noRelated').hide();
|
||||
unrelate_trigger.show();
|
||||
var newwidget = widget.clone()
|
||||
related_dialog.dialog('close');
|
||||
newwidget.find('.id_related_to').click(selectRelated);
|
||||
newwidget.find('.id_no_related_to').click(selectNoRelated);
|
||||
newwidget.find('.relatedLiaisonWidgetTitle').text(link);
|
||||
newwidget.find('.relatedLiaisonWidgetValue').val(pk);
|
||||
newwidget.find('.noRelated').hide();
|
||||
newwidget.find('.id_related_to').hide();
|
||||
newwidget.find('.id_no_related_to').show();
|
||||
widget.before(newwidget);
|
||||
return false;
|
||||
};
|
||||
|
||||
var selectNoRelated = function() {
|
||||
var widget = jQuery(this).parent();
|
||||
widget.find('.relatedLiaisonWidgetTitle').text('');
|
||||
widget.find('.noRelated').show();
|
||||
widget.find('.relatedLiaisonWidgetValue').val('');
|
||||
jQuery(this).hide();
|
||||
widget.remove();
|
||||
return false;
|
||||
};
|
||||
|
||||
|
@ -315,10 +317,9 @@ jQuery(function () {
|
|||
dataType: 'html',
|
||||
success: function(response){
|
||||
related_dialog.html(response);
|
||||
related_dialog.find('th a').click(function() {
|
||||
widget.find('.listURL').text(related_url + jQuery(this).attr('href'));
|
||||
trigger.click();
|
||||
return false;
|
||||
related_dialog.find("#LiaisonListTable").tablesorter({
|
||||
sortList: [[0, 1]],
|
||||
widgets: ["ietf"]
|
||||
});
|
||||
related_dialog.find('td a').click(getRelatedLink);
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue