From b4fd9d3b6b8ca6b8cfc39112d1a4dbb207ca9f47 Mon Sep 17 00:00:00 2001 From: kimakan <45099849+kimakan@users.noreply.github.com> Date: Tue, 19 Sep 2023 11:17:29 +0200 Subject: [PATCH] add visibility conditions to the announcement messages and refactor --- daiquiri/contact/admin.py | 11 ++++- daiquiri/contact/filters.py | 33 +++++++++++++- .../migrations/0007_announcementmessage.py | 13 +++--- daiquiri/contact/models.py | 45 ++++++++++++++++--- daiquiri/contact/settings.py | 1 + .../templates/contact/announcements.html | 2 +- .../contact/templatetags/announcement_tags.py | 6 ++- 7 files changed, 92 insertions(+), 19 deletions(-) create mode 100644 daiquiri/contact/settings.py diff --git a/daiquiri/contact/admin.py b/daiquiri/contact/admin.py index bb29a3f0..d87e8561 100644 --- a/daiquiri/contact/admin.py +++ b/daiquiri/contact/admin.py @@ -1,12 +1,18 @@ +from django import forms from django.contrib import admin -from .models import ContactMessage, AnnouncementMessage +from .models import ContactMessage, AnnouncementMessage, MessageFilter + + +class AnnouncementMessageAdminForm(forms.ModelForm): + visibility_filter = forms.ChoiceField(choices=MessageFilter().CHOICES) @admin.action(description="Make selected messages visible") def make_visible(modeladmin, request, queryset): queryset.update(visible=True) + @admin.action(description="Make selected messages invisible") def make_invisible(modeladmin, request, queryset): queryset.update(visible=False) @@ -16,7 +22,10 @@ class ContactMessageAdmin(admin.ModelAdmin): search_fields = ("subject", "email", "author", "status", "user__username") list_display = ("subject", "email", "author", "status") + class AnnouncementMessageAdmin(admin.ModelAdmin): + form = AnnouncementMessageAdminForm + search_fields = ("title", "announcement") list_display = ("title", "visible", "announcement", "announcement_type", "updated") actions = [make_visible, make_invisible] diff --git a/daiquiri/contact/filters.py b/daiquiri/contact/filters.py index 04947c56..147fedcc 100644 --- a/daiquiri/contact/filters.py +++ b/daiquiri/contact/filters.py @@ -1,11 +1,13 @@ from rest_framework import filters -from .models import ContactMessage - class SpamBackend(filters.BaseFilterBackend): + def filter_queryset(self, request, queryset, view): + + from daiquiri.contact.models import ContactMessage + spam = request.GET.get('spam') if spam is not None: @@ -15,3 +17,30 @@ def filter_queryset(self, request, queryset, view): queryset = queryset.exclude(status=ContactMessage.STATUS_SPAM) return queryset + + + +class DefaultMessageFilter(object): + + CHOICES = ( + ("no_filter", "Show to all users"), + ("logged_in_users", "Show to the logged in users only"), + ("user_has_not_consented", "Show to user who has not consented yet"), + ) + + def no_filter(request): + return True + + def logged_in_users(request): + if request.user.is_authenticated: + return True + return False + + def user_has_not_consented(request): + if request.user.is_authenticated: + if not request.user.profile.consent: + return True + return False + + + diff --git a/daiquiri/contact/migrations/0007_announcementmessage.py b/daiquiri/contact/migrations/0007_announcementmessage.py index 8d9c5ab5..37d9610a 100644 --- a/daiquiri/contact/migrations/0007_announcementmessage.py +++ b/daiquiri/contact/migrations/0007_announcementmessage.py @@ -1,4 +1,4 @@ -# Generated by Django 4.2.4 on 2023-08-08 09:57 +# Generated by Django 4.2.5 on 2023-09-20 07:37 from django.db import migrations, models @@ -14,11 +14,12 @@ class Migration(migrations.Migration): name='AnnouncementMessage', fields=[ ('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), - ('title', models.CharField(blank=True, max_length=100, null=True)), - ('announcement', models.TextField()), - ('announcement_type', models.CharField(choices=[('info', 'info'), ('warning', 'warning'), ('danger', 'urgent')], default='info', max_length=8)), - ('updated', models.DateTimeField(auto_now=True)), - ('visible', models.BooleanField(default=False)), + ('title', models.CharField(blank=True, max_length=100, null=True, verbose_name='Title')), + ('announcement', models.TextField(verbose_name='Announcement')), + ('announcement_type', models.CharField(choices=[('info', 'info'), ('warning', 'warning'), ('danger', 'urgent')], default='info', max_length=8, verbose_name='Announcement type')), + ('updated', models.DateTimeField(auto_now=True, verbose_name='Updated')), + ('visible', models.BooleanField(default=False, verbose_name='Visible')), + ('visibility_filter', models.CharField(default='no_filter', max_length=50, verbose_name='Visibility filter')), ], options={ 'verbose_name': 'Announcement message', diff --git a/daiquiri/contact/models.py b/daiquiri/contact/models.py index c666a597..18612bc5 100644 --- a/daiquiri/contact/models.py +++ b/daiquiri/contact/models.py @@ -1,10 +1,14 @@ +from django.conf import settings from django.contrib.auth.models import User from django.db import models from django.utils.translation import gettext_lazy as _ +from daiquiri.core.utils import import_class + class ContactMessage(models.Model): + STATUS_ACTIVE = 'ACTIVE' STATUS_CLOSED = 'CLOSED' STATUS_SPAM = 'SPAM' @@ -46,24 +50,48 @@ def set_status_spam(self): self.save() + +def MessageFilter(): + return import_class(settings.ANNOUNCEMENT_MESSAGE_FILTER) + class AnnouncementMessage(models.Model): # alert types must correspond to the bootstrap alert types ALERT_TYPE_INFO = "info" ALERT_TYPE_WARNING = "warning" - ALERT_TYPE_ERROR = "danger" + ALERT_TYPE_URGENT = "danger" ANNOUNCEMENT_TYPE_CHOICES = ( (ALERT_TYPE_INFO, "info"), (ALERT_TYPE_WARNING, "warning"), - (ALERT_TYPE_ERROR, "urgent"), + (ALERT_TYPE_URGENT, "urgent"), ) - title = models.CharField(max_length=100, blank=True, null=True) - announcement = models.TextField() - announcement_type = models.CharField(max_length=8, choices=ANNOUNCEMENT_TYPE_CHOICES, default=ALERT_TYPE_INFO) - updated = models.DateTimeField(auto_now=True) - visible = models.BooleanField(default=False) + title = models.CharField( + max_length=100, blank=True, null=True, + verbose_name=_("Title") + ) + announcement = models.TextField( + verbose_name=_("Announcement") + ) + announcement_type = models.CharField( + max_length=8, + choices=ANNOUNCEMENT_TYPE_CHOICES, + default=ALERT_TYPE_INFO, + verbose_name=_("Announcement type") + ) + updated = models.DateTimeField( + auto_now=True, + verbose_name=_("Updated") + ) + visible = models.BooleanField( + default=False, + verbose_name=_("Visible") + ) + visibility_filter = models.CharField( + max_length=50, default="no_filter", + verbose_name="Visibility filter" + ) class Meta: ordering = ('-updated', 'title') @@ -74,3 +102,6 @@ class Meta: def __str__(self): return f"{self.title}: '{self.announcement}'" + def get_filter(self): + return getattr(MessageFilter(), str(self.visibility_filter)) + diff --git a/daiquiri/contact/settings.py b/daiquiri/contact/settings.py new file mode 100644 index 00000000..3654671d --- /dev/null +++ b/daiquiri/contact/settings.py @@ -0,0 +1 @@ +ANNOUNCEMENT_MESSAGE_FILTER = 'daiquiri.contact.filters.DefaultMessageFilter' diff --git a/daiquiri/contact/templates/contact/announcements.html b/daiquiri/contact/templates/contact/announcements.html index 6b650064..f85417b8 100644 --- a/daiquiri/contact/templates/contact/announcements.html +++ b/daiquiri/contact/templates/contact/announcements.html @@ -2,7 +2,7 @@ {% for msg in announcements %} {% endfor %} {% endif %} diff --git a/daiquiri/contact/templatetags/announcement_tags.py b/daiquiri/contact/templatetags/announcement_tags.py index 605af6ba..7d42bd4b 100644 --- a/daiquiri/contact/templatetags/announcement_tags.py +++ b/daiquiri/contact/templatetags/announcement_tags.py @@ -4,9 +4,11 @@ register = template.Library() -@register.inclusion_tag("contact/announcements.html") -def show_announcements(): +@register.inclusion_tag("contact/announcements.html", takes_context=True) +def show_announcements(context): + request = context["request"] announcements = AnnouncementMessage.objects.filter(visible=True) + announcements = [msg for msg in announcements if msg.get_filter()(request) is True] return { "announcements": announcements, }