From bd35e4e21e6d90befeaf10a7156e921ab55c40ff Mon Sep 17 00:00:00 2001
From: Yohann D'ANELLO <yohann.danello@gmail.com>
Date: Fri, 31 Jul 2020 13:17:16 +0200
Subject: [PATCH] Separate club members in a dedicated page (WIP)

---
 apps/member/urls.py                |  1 +
 apps/member/views.py               | 40 +++++++++++++++++++++++++++-
 locale/de/LC_MESSAGES/django.po    |  2 +-
 locale/fr/LC_MESSAGES/django.po    |  4 +--
 templates/member/club_info.html    |  2 +-
 templates/member/club_members.html | 42 ++++++++++++++++++++++++++++++
 templates/member/club_tables.html  |  4 +--
 7 files changed, 88 insertions(+), 7 deletions(-)
 create mode 100644 templates/member/club_members.html

diff --git a/apps/member/urls.py b/apps/member/urls.py
index 4be4ceae..359a8846 100644
--- a/apps/member/urls.py
+++ b/apps/member/urls.py
@@ -16,6 +16,7 @@ urlpatterns = [
     path('club/<int:pk>/update/', views.ClubUpdateView.as_view(), name="club_update"),
     path('club/<int:pk>/update_pic/', views.ClubPictureUpdateView.as_view(), name="club_update_pic"),
     path('club/<int:pk>/aliases/', views.ClubAliasView.as_view(), name="club_alias"),
+    path('club/<int:pk>/members/', views.ClubMembersListView.as_view(), name="club_members"),
 
     path('user/', views.UserListView.as_view(), name="user_list"),
     path('user/<int:pk>/', views.UserDetailView.as_view(), name="user_detail"),
diff --git a/apps/member/views.py b/apps/member/views.py
index 51f31445..1785d1ad 100644
--- a/apps/member/views.py
+++ b/apps/member/views.py
@@ -13,6 +13,7 @@ from django.contrib.auth.views import LoginView
 from django.db.models import Q
 from django.shortcuts import redirect
 from django.urls import reverse_lazy
+from django.utils import timezone
 from django.utils.translation import gettext_lazy as _
 from django.views.generic import CreateView, DetailView, UpdateView, TemplateView
 from django.views.generic.edit import FormMixin
@@ -349,7 +350,7 @@ class ClubDetailView(ProtectQuerysetMixin, LoginRequiredMixin, DetailView):
         ).filter(PermissionBackend.filter_queryset(self.request.user, Membership, "view"))
 
         membership_table = MembershipTable(data=club_member, prefix="membership-")
-        membership_table.paginate(per_page=20, page=self.request.GET.get('membership-page', 1))
+        membership_table.paginate(per_page=5, page=self.request.GET.get('membership-page', 1))
         context['member_list'] = membership_table
 
         # Check if the user has the right to create a membership, to display the button.
@@ -652,3 +653,40 @@ class ClubManageRolesView(ProtectQuerysetMixin, LoginRequiredMixin, UpdateView):
 
     def get_success_url(self):
         return reverse_lazy('member:user_detail', kwargs={'pk': self.object.user.id})
+
+
+class ClubMembersListView(ProtectQuerysetMixin, LoginRequiredMixin, SingleTableView):
+    model = Membership
+    table_class = MembershipTable
+    template_name = "member/club_members.html"
+    extra_context = {"title": _("Members of the club")}
+
+    def get_queryset(self, **kwargs):
+        qs = super().get_queryset().filter(club_id=self.kwargs["pk"])
+
+        if 'search' in self.request.GET:
+            pattern = self.request.GET['search']
+            qs = qs.filter(
+                Q(user__first_name__iregex='^' + pattern) |
+                Q(user__last_name__iregex='^' + pattern) |
+                Q(user__note__alias__normalized_name__iregex='^' + Alias.normalize(pattern))
+            )
+
+        if 'only_active' in self.request.GET:
+            only_active = self.request.GET["only_active"] != '0'
+        else:
+            only_active = True
+
+        if only_active:
+            qs = qs.filter(date_start__lte=timezone.now().today(), date_end__gte=timezone.now().today())
+
+        qs = qs.order_by('-date_start', 'user__username')
+
+        return qs.distinct()
+
+    def get_context_data(self, **kwargs):
+        context = super().get_context_data(**kwargs)
+        context["club"] = Club.objects.filter(
+            PermissionBackend.filter_queryset(self.request.user, Club, "view")
+        ).get(pk=self.kwargs["pk"])
+        return context
\ No newline at end of file
diff --git a/locale/de/LC_MESSAGES/django.po b/locale/de/LC_MESSAGES/django.po
index e4526352..c9ac11ba 100644
--- a/locale/de/LC_MESSAGES/django.po
+++ b/locale/de/LC_MESSAGES/django.po
@@ -1829,7 +1829,7 @@ msgid "Club listing"
 msgstr ""
 
 #: templates/member/club_tables.html:7
-msgid "Member of the Club"
+msgid "Club members"
 msgstr ""
 
 #: templates/member/club_tables.html:20 templates/member/profile_tables.html:28
diff --git a/locale/fr/LC_MESSAGES/django.po b/locale/fr/LC_MESSAGES/django.po
index 35ecff90..c561abba 100644
--- a/locale/fr/LC_MESSAGES/django.po
+++ b/locale/fr/LC_MESSAGES/django.po
@@ -1889,8 +1889,8 @@ msgid "Club listing"
 msgstr "Liste des clubs"
 
 #: templates/member/club_tables.html:7
-msgid "Member of the Club"
-msgstr "Membre du club"
+msgid "Club members"
+msgstr "Membres du club"
 
 #: templates/member/club_tables.html:20 templates/member/profile_tables.html:28
 #: templates/wei/weiclub_tables.html:105
diff --git a/templates/member/club_info.html b/templates/member/club_info.html
index 18cfe631..e7974f77 100644
--- a/templates/member/club_info.html
+++ b/templates/member/club_info.html
@@ -11,7 +11,7 @@
     <div class="card-body" id="profile_infos">
         <dl class="row">
             <dt class="col-xl-6">{% trans 'name'|capfirst %}</dt>
-            <dd class="col-xl-6">{{ club.name}}</dd>
+            <dd class="col-xl-6">{{ club.name }}</dd>
 
             {% if club.parent_club %}
                 <dt class="col-xl-6"><a href="{% url 'member:club_detail' club.parent_club.pk %}">{% trans 'Club Parent'|capfirst %}</a></dt>
diff --git a/templates/member/club_members.html b/templates/member/club_members.html
new file mode 100644
index 00000000..fca6ec1c
--- /dev/null
+++ b/templates/member/club_members.html
@@ -0,0 +1,42 @@
+{% extends "member/noteowner_detail.html" %}
+{% load i18n %}
+{% load render_table from django_tables2 %}
+
+{% block profile_info %}
+{% include "member/club_info.html" %}
+{% endblock %}
+
+{% block profile_content %}
+    <input id="searchbar" type="text" class="form-control" placeholder="Nom/prénom/note ...">
+    <hr>
+
+    <div id="memberships_table">
+        {% if table.data %}
+            {% render_table table %}
+        {% else %}
+            <div class="alert alert-warning">
+                {% trans "There is no membership found with this pattern." %}
+            </div>
+        {% endif %}
+    </div>
+{% endblock %}
+
+{% block extrajavascript %}
+<script type="text/javascript">
+    $(document).ready(function() {
+        let old_pattern = null;
+        let searchbar_obj = $("#searchbar");
+
+        function reloadTable() {
+            let pattern = searchbar_obj.val();
+
+            if (pattern === old_pattern)
+                return;
+
+            $("#memberships_table").load(location.pathname + "?search=" + pattern.replace(" ", "%20") + " #memberships_table");
+        }
+
+        searchbar_obj.keyup(reloadTable);
+    });
+</script>
+{% endblock %}
diff --git a/templates/member/club_tables.html b/templates/member/club_tables.html
index e937fbe9..92d66425 100644
--- a/templates/member/club_tables.html
+++ b/templates/member/club_tables.html
@@ -3,8 +3,8 @@
 {% if member_list.data %}
     <div class="card">
         <div class="card-header position-relative" id="clubListHeading">
-            <a class="btn btn-link stretched-link font-weight-bold">
-                <i class="fa fa-users"></i> {% trans "Member of the Club" %}
+            <a class="btn btn-link stretched-link font-weight-bold" href="{% url 'member:club_members' pk=club.pk %}">
+                <i class="fa fa-users"></i> {% trans "Club members" %}
             </a>
         </div>
         {% render_table member_list %}
-- 
GitLab