diff --git a/apps/activity/views.py b/apps/activity/views.py index 7829a2ee..50607ceb 100644 --- a/apps/activity/views.py +++ b/apps/activity/views.py @@ -152,9 +152,11 @@ class ActivityDetailView(ProtectQuerysetMixin, LoginRequiredMixin, MultiTableMix def get_tables_data(self): return [ Guest.objects.filter(activity=self.object) - .filter(PermissionBackend.filter_queryset(self.request, Guest, "view")), + .filter(PermissionBackend.filter_queryset(self.request, Guest, "view")) + .distinct(), self.object.opener.filter(activity=self.object) - .filter(PermissionBackend.filter_queryset(self.request, Opener, "view")), + .filter(PermissionBackend.filter_queryset(self.request, Opener, "view")) + .distinct(), ] def render_to_response(self, context, **response_kwargs): @@ -309,7 +311,7 @@ class ActivityInviteView(ProtectQuerysetMixin, ProtectedCreateView): @transaction.atomic def form_valid(self, form): form.instance.activity = Activity.objects\ - .filter(PermissionBackend.filter_queryset(self.request, Activity, "view")).get(pk=self.kwargs["pk"]) + .filter(PermissionBackend.filter_queryset(self.request, Activity, "view")).distinct().get(pk=self.kwargs["pk"]) return super().form_valid(form) def get_success_url(self, **kwargs): diff --git a/apps/member/views.py b/apps/member/views.py index 72ad446e..84275db1 100644 --- a/apps/member/views.py +++ b/apps/member/views.py @@ -50,6 +50,15 @@ class CustomLoginView(LoginView): self.request.session['permission_mask'] = form.cleaned_data['permission_mask'].rank return super().form_valid(form) + def get_context_data(self, **kwargs): + context = super().get_context_data(**kwargs) + user_agent = self.request.META.get('HTTP_USER_AGENT', '').lower() + + context['display_appstore_badge'] = 'iphone' in user_agent or 'android' not in user_agent + context['display_playstore_badge'] = 'android' in user_agent or 'iphone' not in user_agent + + return context + class UserUpdateView(ProtectQuerysetMixin, LoginRequiredMixin, UpdateView): """ diff --git a/apps/permission/fixtures/initial.json b/apps/permission/fixtures/initial.json index 0acd11c4..f6d90b31 100644 --- a/apps/permission/fixtures/initial.json +++ b/apps/permission/fixtures/initial.json @@ -927,7 +927,7 @@ "note", "transactiontemplate" ], - "query": "{\"destination\": [\"club\", \"note\"]}", + "query": "[\"AND\", {\"destination\": [\"club\", \"note\"]}, {\"category__name\": \"Clubs\"}]", "type": "view", "mask": 2, "field": "", @@ -943,7 +943,7 @@ "note", "transactiontemplate" ], - "query": "{\"destination\": [\"club\", \"note\"]}", + "query": "[\"AND\", {\"destination\": [\"club\", \"note\"]}, {\"category__name\": \"Clubs\"}]", "type": "add", "mask": 3, "field": "", @@ -959,7 +959,7 @@ "note", "transactiontemplate" ], - "query": "{\"destination\": [\"club\", \"note\"]}", + "query": "[\"AND\", {\"destination\": [\"club\", \"note\"]}, {\"category__name\": \"Clubs\"}]", "type": "change", "mask": 3, "field": "", @@ -3484,7 +3484,23 @@ "mask": 1, "permanent": false, "description": "Voir la bouffe servie" - } + } + }, + { + "model": "permission.permission", + "pk": 223, + "fields": { + "model": [ + "note", + "templatecategory" + ], + "query": "{\"name\": \"Clubs\"}", + "type": "view", + "mask": 2, + "field": "", + "permanent": false, + "description": "Voir la catégorie de bouton Clubs" + } }, { "model": "permission.permission", @@ -4896,7 +4912,6 @@ 19, 20, 21, - 27, 59, 60, 61, @@ -4907,6 +4922,7 @@ 182, 184, 185, + 223, 239, 240, 241 @@ -5271,6 +5287,12 @@ 176, 177, 197, + 211, + 212, + 213, + 214, + 215, + 216, 311, 319 ] diff --git a/apps/treasury/models.py b/apps/treasury/models.py index 63e1d7cd..227773b7 100644 --- a/apps/treasury/models.py +++ b/apps/treasury/models.py @@ -338,13 +338,13 @@ class SogeCredit(models.Model): last_name=self.user.last_name, first_name=self.user.first_name, bank="Société générale", - valid=False, + valid=True, ) credit_transaction._force_save = True credit_transaction.save() credit_transaction.refresh_from_db() self.credit_transaction = credit_transaction - elif not self.valid_legacy: + elif not self.valid: self.credit_transaction.amount = self.amount self.credit_transaction._force_save = True self.credit_transaction.save() @@ -371,7 +371,7 @@ class SogeCredit(models.Model): The Sogé credit may be created after the user already paid its memberships. We query transactions and update the credit, if it is unvalid. """ - if self.valid_legacy or not self.pk: + if self.valid or not self.pk: return # Soge do not pay BDE and kfet memberships since 2022 @@ -403,7 +403,7 @@ class SogeCredit(models.Model): self.transactions.add(m.transaction) for tr in self.transactions.all(): - tr.valid = False + tr.valid = True tr.save() def invalidate(self): @@ -411,7 +411,7 @@ class SogeCredit(models.Model): Invalidating a Société générale delete the transaction of the bank if it was already created. Treasurers must know what they do, With Great Power Comes Great Responsibility... """ - if self.valid_legacy: + if self.valid: self.credit_transaction.valid = False self.credit_transaction.save() for tr in self.transactions.all(): @@ -420,7 +420,7 @@ class SogeCredit(models.Model): tr.save() def validate(self, force=False): - if self.valid_legacy and not force: + if self.valid and not force: # The credit is already done return @@ -428,6 +428,7 @@ class SogeCredit(models.Model): self.invalidate() # Refresh credit amount self.save() + self.valid = True self.credit_transaction.valid = True self.credit_transaction._force_save = True self.credit_transaction.save() diff --git a/apps/treasury/tables.py b/apps/treasury/tables.py index cf17a2c8..2931e800 100644 --- a/apps/treasury/tables.py +++ b/apps/treasury/tables.py @@ -56,6 +56,7 @@ class InvoiceTable(tables.Table): model = Invoice template_name = 'django_tables2/bootstrap4.html' fields = ('id', 'name', 'object', 'acquitted', 'invoice',) + order_by = ('-id',) class RemittanceTable(tables.Table): diff --git a/apps/treasury/tests/test_treasury.py b/apps/treasury/tests/test_treasury.py index d1d5a414..8feb5485 100644 --- a/apps/treasury/tests/test_treasury.py +++ b/apps/treasury/tests/test_treasury.py @@ -359,7 +359,7 @@ class TestSogeCredits(TestCase): )) self.assertRedirects(response, reverse("treasury:manage_soge_credit", args=(soge_credit.pk,)), 302, 200) soge_credit.refresh_from_db() - self.assertTrue(soge_credit.valid_legacy) + self.assertTrue(soge_credit.valid) self.user.note.refresh_from_db() self.assertEqual( Transaction.objects.filter(Q(source=self.user.note) | Q(destination=self.user.note)).count(), 3) diff --git a/apps/treasury/views.py b/apps/treasury/views.py index eb2fd0d7..3d4b4397 100644 --- a/apps/treasury/views.py +++ b/apps/treasury/views.py @@ -417,7 +417,7 @@ class SogeCreditListView(LoginRequiredMixin, ProtectQuerysetMixin, SingleTableVi ) if "valid" not in self.request.GET or not self.request.GET["valid"]: - qs = qs.filter(credit_transaction__valid=False) + qs = qs.filter(valid=False) return qs diff --git a/apps/wei/tests/test_wei_registration.py b/apps/wei/tests/test_wei_registration.py index ca8f08e9..18e93504 100644 --- a/apps/wei/tests/test_wei_registration.py +++ b/apps/wei/tests/test_wei_registration.py @@ -680,7 +680,7 @@ class TestWEIRegistration(TestCase): self.assertTrue(soge_credit.exists()) soge_credit = soge_credit.get() self.assertTrue(membership.transaction in soge_credit.transactions.all()) - self.assertFalse(membership.transaction.valid) + self.assertTrue(membership.transaction.valid) # Check that if the WEI is started, we can't update a wei self.wei.date_start = date(2000, 1, 1) diff --git a/locale/de/LC_MESSAGES/django.po b/locale/de/LC_MESSAGES/django.po index 7ca27bd5..af34ba7e 100644 --- a/locale/de/LC_MESSAGES/django.po +++ b/locale/de/LC_MESSAGES/django.po @@ -4366,6 +4366,14 @@ msgstr "" msgid "Forgotten your password or username?" msgstr "Passwort oder Username vergessen?" +#: note_kfet/templates/registration/login.html:44 +msgid "Download on the AppStore" +msgstr "Im AppStore herunterladen" + +#: note_kfet/templates/registration/login.html:48 +msgid "Get it on Google Play" +msgstr "Bei Google Play herunterladen" + #: note_kfet/templates/registration/password_change_done.html:13 msgid "Your password was changed." msgstr "Ihr Passwort wurde geändert." diff --git a/locale/es/LC_MESSAGES/django.po b/locale/es/LC_MESSAGES/django.po index 6612e6ec..d737aa21 100644 --- a/locale/es/LC_MESSAGES/django.po +++ b/locale/es/LC_MESSAGES/django.po @@ -4281,6 +4281,14 @@ msgstr "" msgid "Forgotten your password or username?" msgstr "¿ Contraseña o nombre de usuario olvidado ?" +#: note_kfet/templates/registration/login.html:44 +msgid "Download on the AppStore" +msgstr "Descargar en la AppStore" + +#: note_kfet/templates/registration/login.html:48 +msgid "Get it on Google Play" +msgstr "Descargar en Google Play" + #: note_kfet/templates/registration/password_change_done.html:13 msgid "Your password was changed." msgstr "Su contraseña fue cambiada con éxito." diff --git a/locale/fr/LC_MESSAGES/django.po b/locale/fr/LC_MESSAGES/django.po index 2f3c6752..96f1621b 100644 --- a/locale/fr/LC_MESSAGES/django.po +++ b/locale/fr/LC_MESSAGES/django.po @@ -4584,6 +4584,14 @@ msgstr "" msgid "Forgotten your password or username?" msgstr "Mot de passe ou pseudo oublié ?" +#: note_kfet/templates/registration/login.html:44 +msgid "Download on the AppStore" +msgstr "Télécharger sur l'AppStore" + +#: note_kfet/templates/registration/login.html:48 +msgid "Get it on Google Play" +msgstr "Télécharger sur Google Play" + #: note_kfet/templates/registration/password_change_done.html:13 msgid "Your password was changed." msgstr "Votre mot de passe a bien été changé." diff --git a/note_kfet/static/img/appstore_badge_fr.svg b/note_kfet/static/img/appstore_badge_fr.svg new file mode 100644 index 00000000..329e8dc3 --- /dev/null +++ b/note_kfet/static/img/appstore_badge_fr.svg @@ -0,0 +1,50 @@ + + Download_on_the_App_Store_Badge_FR_RGB_blk_100517 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/note_kfet/static/img/appstore_badge_fr_preorder.svg b/note_kfet/static/img/appstore_badge_fr_preorder.svg new file mode 100644 index 00000000..891fe91e --- /dev/null +++ b/note_kfet/static/img/appstore_badge_fr_preorder.svg @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/note_kfet/static/img/playstore_badge_fr.svg b/note_kfet/static/img/playstore_badge_fr.svg new file mode 100644 index 00000000..137e9e90 --- /dev/null +++ b/note_kfet/static/img/playstore_badge_fr.svg @@ -0,0 +1,63 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/note_kfet/static/img/playstore_badge_fr_preorder.svg b/note_kfet/static/img/playstore_badge_fr_preorder.svg new file mode 100644 index 00000000..558a7f66 --- /dev/null +++ b/note_kfet/static/img/playstore_badge_fr_preorder.svg @@ -0,0 +1,66 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/note_kfet/templates/registration/login.html b/note_kfet/templates/registration/login.html index b30c9fb6..6523f529 100644 --- a/note_kfet/templates/registration/login.html +++ b/note_kfet/templates/registration/login.html @@ -39,6 +39,23 @@ SPDX-License-Identifier: GPL-2.0-or-later {% trans 'Forgotten your password or username?' %} + +
+ {% now "Ymd" as current_date_str %} + + {% if display_appstore_badge %} + + {% trans 'Download on the AppStore' %} + + {% endif %} + {% if display_playstore_badge %} + + {% trans 'Get it on Google Play' %} + + {% endif %} +
{% endblock %} \ No newline at end of file