extensions-website/abuse/forms.py
Oleg Komarov 012845c712 Abuse reports: moderator form for resolving/dismissing + notification (#173)
It is possible to submit the form update the note and status multiple times,
e.g. a report that was initially dismissed, can be resolved later.
Each valid form submission will generate a notification for the reporter.

Once a note is saved, it becomes visible to the reporter.

The migration in this PR replaces the AbuseReport status Confirmed(=2)
that wasn't used in production with Dismissed(=2). Assuming that this is
a minor sin while the project is still in beta.

Reviewed-on: #173
Reviewed-by: Anna Sirota <annasirota@noreply.localhost>
2024-06-07 17:04:52 +02:00

69 lines
2.0 KiB
Python

import logging
from django import forms
from django.core.exceptions import ValidationError
from common import compare
import releases.models
import abuse.models
logger = logging.getLogger(__name__)
class ReportExtensionForm(forms.ModelForm):
class Meta:
model = abuse.models.AbuseReport
fields = ('reason', 'version', 'message')
widgets = {
'version': forms.Select,
}
def __init__(self, *args, **kwargs):
"""Limit 'version' choices to known releases."""
super().__init__(*args, **kwargs)
self.fields['version'].widget.choices = tuple(releases.models.Release.as_choices()) + (
(None, 'Other'),
)
def clean_version(self):
field = 'version'
if not self.cleaned_data.get(field):
# Assume that 'required' part of the validation is done already
return
try:
return compare.version(self.cleaned_data[field])
except ValidationError as e:
self.add_error(field, forms.ValidationError([e.message], code='invalid'))
class ReportRatingForm(forms.ModelForm):
class Meta:
model = abuse.models.AbuseReport
fields = ('reason', 'message')
class ResolveReportForm(forms.ModelForm):
class Meta:
model = abuse.models.AbuseReport
fields = ('moderator_note',)
def __init__(self, *args, **kwargs):
self.request = kwargs.pop('request')
super().__init__(*args, **kwargs)
self.fields['moderator_note'].required = True
def clean(self):
super().clean()
if 'dismiss' in self.data:
self.instance.status = self.instance.STATUSES.DISMISSED
if 'resolve' in self.data:
self.instance.status = self.instance.STATUSES.RESOLVED
self.instance.processed_by = self.request.user
return self.cleaned_data
def is_valid(self, *args, **kwargs) -> bool:
if 'dismiss' not in self.data and 'resolve' not in self.data:
return False
return super().is_valid(*args, **kwargs)