membershipworks: Add view for event registrations

This commit is contained in:
Adam Goldsmith 2024-05-05 23:20:25 -04:00
parent 25fbe3d352
commit 9c2084903f
5 changed files with 108 additions and 0 deletions

View File

@ -65,6 +65,30 @@ class EventTable(tables.Table):
} }
class EventRegistrationsTable(tables.Table):
ticket_count = tables.Column(empty_values=())
name = tables.Column(accessor="Full name")
email = tables.EmailColumn(accessor="Email")
phone = tables.Column(accessor="Phone")
emergency_contact_name = tables.Column(accessor="Emergency Contact Name:")
emergency_contact_phone_number = tables.Column(
accessor="Emergency Contact Phone Number:"
)
emergency_contact_relation = tables.Column(accessor="Emergency Contact Relation:")
def render_ticket_count(self, record):
return sum(int(v) for k, v in record.items() if k.startswith("Ticket: "))
class Meta:
row_attrs = {
"class": lambda table, record: (
""
if table.render_ticket_count(record) > 0
else "text-decoration-line-through table-danger"
)
}
class EventSummaryTable(tables.Table): class EventSummaryTable(tables.Table):
event_count = tables.Column("Events") event_count = tables.Column("Events")
canceled_event_count = tables.Column("Canceled Events") canceled_event_count = tables.Column("Canceled Events")

View File

@ -13,6 +13,10 @@
{% endblock %} {% endblock %}
{% block content %} {% block content %}
<div class="container"> <div class="container">
{% if event.registrations is not None %}
{% url 'membershipworks:event-registrations' event.pk as registrations_url %}
{% bootstrap_button href=registrations_url content="Show Registrations" %}
{% endif %}
{% include "membershipworks/event_invoice.dj.html" %} {% include "membershipworks/event_invoice.dj.html" %}
<div class="card w-auto mt-5"> <div class="card w-auto mt-5">

View File

@ -0,0 +1,29 @@
{% extends "base.dj.html" %}
{% load nh3_tags %}
{% load render_table from django_tables2 %}
{% load django_bootstrap5 %}
{% block title %}Registrations for {{ event.details.ttl|nh3 }}{% endblock %}
{% block admin_link %}
{% url 'admin:membershipworks_eventext_change' event.pk %}
{% endblock %}
{% block breadcrumbs %}
{% include "./components/event_breadcrumbs.dj.html" %}
<li class="breadcrumb-item">
<a href="{% url 'membershipworks:event-detail' event.pk %}">{{ event.details.ttl|nh3|truncatechars_html:40 }}</a>
</li>
<li class="breadcrumb-item active" aria-current="page">Registrations</li>
{% endblock %}
{% block content %}
<div class="container">
<div class="row justify-content-center">
<div class="col-auto">
{% bootstrap_button extra_classes="btn-sm" href=email_link target="_blank" content="Email all attendees" %}
</div>
<div class="col-auto">{% include "cmsmanage/components/download_table.dj.html" %}</div>
</div>
{% render_table table %}
<p class="text-center">Data last updated {{ event.details_timestamp }}</p>
</div>
{% endblock %}

View File

@ -45,6 +45,11 @@ urlpatterns = [
views.EventDetailView.as_view(), views.EventDetailView.as_view(),
name="event-detail", name="event-detail",
), ),
path(
"event/<eid>/registrations",
views.EventRegistrationsView.as_view(),
name="event-registrations",
),
path( path(
"event/invoice/<uuid:uuid>.pdf", "event/invoice/<uuid:uuid>.pdf",
views.EventInvoicePDFView.as_view(), views.EventInvoicePDFView.as_view(),

View File

@ -1,6 +1,7 @@
import uuid import uuid
from datetime import datetime from datetime import datetime
from typing import Any from typing import Any
from urllib.parse import quote, urlencode
from django.conf import settings from django.conf import settings
from django.contrib import messages from django.contrib import messages
@ -46,6 +47,7 @@ from .invoice_email import make_invoice_emails
from .models import EventAttendee, EventExt, EventInvoice, Member from .models import EventAttendee, EventExt, EventInvoice, Member
from .tables import ( from .tables import (
EventAttendeeTable, EventAttendeeTable,
EventRegistrationsTable,
EventSummaryTable, EventSummaryTable,
EventTable, EventTable,
InvoiceTable, InvoiceTable,
@ -418,6 +420,50 @@ class EventInvoicePDFView(AccessMixin, BaseDetailView):
return self.handle_no_permission() return self.handle_no_permission()
class EventRegistrationsView(ExportMixin, SingleTableMixin, AccessMixin, DetailView):
permission_required = "membershipworks.view_eventext"
model = EventExt
pk_url_kwarg = "eid"
context_object_name = "event"
template_name = "membershipworks/event_registrations.dj.html"
table_class = EventRegistrationsTable
export_formats = ("csv", "xlsx", "ods")
def render_to_response(
self, context: dict[str, Any], **response_kwargs: Any
) -> HttpResponse:
if self.request.user.has_perm(
self.permission_required
) or self.object.user_is_instructor(self.request.user):
return super().render_to_response(context, **response_kwargs)
else:
return self.handle_no_permission()
def get_context_data(self, **kwargs: Any) -> dict[str, Any]:
context_data = super().get_context_data(**kwargs)
context_data["email_link"] = "mailto:?" + urlencode(
{
"subject": f"[CMS Event] {self.object.title}",
"bcc": ",".join(
mail.message.sanitize_address(
(reg["Full name"], reg["Email"]), settings.DEFAULT_CHARSET
)
for reg in self.object.registrations
if any(
int(v) > 0 for k, v in reg.items() if k.startswith("Ticket: ")
)
),
},
quote_via=quote,
)
return context_data
def get_table_data(self):
return self.object.registrations
class EventAttendeeFilters(django_filters.FilterSet): class EventAttendeeFilters(django_filters.FilterSet):
new_since = django_filters.DateFilter( new_since = django_filters.DateFilter(
field_name="event__start", method="filter_new_since" field_name="event__start", method="filter_new_since"