Files
postgres-web/pgweb/core/forms.py
Magnus Hagander 5d0b64a5ab Re-implement modification notifications in simple_form
The way signals are sent for many2many apparently changed completely
between the python2 and python3 versions of the same Django version,
which broke the way we did this before. And it was always a bit of a
hack...

Instead, reimplement notifications in the simple_form handler. This now
also consolidates regular field notificationss and many2many
notifications in a much cleaner way.

This will, however, *only* have an effect on changes made through
simple_form. Luckily that's the most common way we handle forms, with
the exception being /admin/. So leave the old code in place to handle
the changes through /admin/, as well as the deletion of objects.

In the end the only thing lost is the ability to get m2m differences
when an admin makes changes, and that's the least important of all
notification. And as a bonus, the regular change notifications and in
particular "new item" notifications look a lot nicer.
2019-01-26 16:19:26 +01:00

82 lines
3.3 KiB
Python

from django import forms
from django.forms import ValidationError
from django.conf import settings
from .models import Organisation
from django.contrib.auth.models import User
from pgweb.util.middleware import get_current_user
from pgweb.mailqueue.util import send_simple_mail
class OrganisationForm(forms.ModelForm):
remove_manager = forms.ModelMultipleChoiceField(required=False, queryset=None, label="Current manager(s)", help_text="Select one or more managers to remove")
add_manager = forms.EmailField(required=False)
class Meta:
model = Organisation
exclude = ('lastconfirmed', 'approved', 'managers', )
def __init__(self, *args, **kwargs):
super(OrganisationForm, self).__init__(*args, **kwargs)
if self.instance and self.instance.pk:
self.fields['remove_manager'].queryset = self.instance.managers.all()
else:
del self.fields['remove_manager']
del self.fields['add_manager']
def clean_add_manager(self):
if self.cleaned_data['add_manager']:
# Something was added as manager - let's make sure the user exists
try:
User.objects.get(email=self.cleaned_data['add_manager'].lower())
except User.DoesNotExist:
raise ValidationError("User with email %s not found" % self.cleaned_data['add_manager'])
return self.cleaned_data['add_manager']
def clean_remove_manager(self):
if self.cleaned_data['remove_manager']:
removecount = 0
for toremove in self.cleaned_data['remove_manager']:
if toremove in self.instance.managers.all():
removecount += 1
if len(self.instance.managers.all()) - removecount <= 0:
raise ValidationError("Cannot remove all managers from an organsation!")
return self.cleaned_data['remove_manager']
def save(self, commit=True):
model = super(OrganisationForm, self).save(commit=False)
ops = []
if 'add_manager' in self.cleaned_data and self.cleaned_data['add_manager']:
u = User.objects.get(email=self.cleaned_data['add_manager'].lower())
model.managers.add(u)
ops.append('Added manager {}'.format(u.username))
if 'remove_manager' in self.cleaned_data and self.cleaned_data['remove_manager']:
for toremove in self.cleaned_data['remove_manager']:
model.managers.remove(toremove)
ops.append('Removed manager {}'.format(toremove.username))
if ops:
send_simple_mail(
settings.NOTIFICATION_FROM,
settings.NOTIFICATION_EMAIL,
"{0} modified managers of {1}".format(get_current_user().username, model),
"The following changes were made to managers:\n\n{0}".format("\n".join(ops))
)
return model
def apply_submitter(self, model, User):
model.managers.add(User)
class MergeOrgsForm(forms.Form):
merge_into = forms.ModelChoiceField(queryset=Organisation.objects.all())
merge_from = forms.ModelChoiceField(queryset=Organisation.objects.all())
def clean(self):
if self.cleaned_data['merge_into'] == self.cleaned_data['merge_from']:
raise ValidationError("The two organisations selected must be different!")
return self.cleaned_data