From 1ce4887b795d6f8dffab1d340d2f1011926f6ac0 Mon Sep 17 00:00:00 2001 From: vasileios Date: Mon, 26 Jun 2023 12:40:36 +0200 Subject: [PATCH] [#1566] Added email registration to case detail --- .../cms/cases/tests/test_contactform.py | 135 +++++++++++++++++- src/open_inwoner/cms/cases/views/status.py | 93 +++++++++--- src/open_inwoner/openklant/models.py | 6 +- .../scss/components/Cases/Cases.scss | 4 + 4 files changed, 217 insertions(+), 21 deletions(-) diff --git a/src/open_inwoner/cms/cases/tests/test_contactform.py b/src/open_inwoner/cms/cases/tests/test_contactform.py index 1650f64414..11a00c8a92 100644 --- a/src/open_inwoner/cms/cases/tests/test_contactform.py +++ b/src/open_inwoner/cms/cases/tests/test_contactform.py @@ -197,10 +197,70 @@ def _setUpMocks(self, m): ), ] - def test_form_is_shown_if_open_klant_configured(self, m): + def _setUpExtraMocks(self, m): + self.contactmoment = generate_oas_component( + "cmc", + "schemas/ContactMoment", + uuid="aaaaaaaa-aaaa-aaaa-aaaa-bbbbbbbbbbbb", + url=f"{CONTACTMOMENTEN_ROOT}contactmoment/aaaaaaaa-aaaa-aaaa-aaaa-bbbbbbbbbbbb", + status=Status.nieuw, + antwoord="", + text="hey!\n\nwaddup?", + ) + self.klant_contactmoment = generate_oas_component( + "cmc", + "schemas/KlantContactMoment", + uuid="aaaaaaaa-aaaa-aaaa-aaaa-cccccccccccc", + url=f"{CONTACTMOMENTEN_ROOT}klantcontactmomenten/aaaaaaaa-aaaa-aaaa-aaaa-cccccccccccc", + klant=self.klant["url"], + contactmoment=self.contactmoment["url"], + ) + m.post( + f"{CONTACTMOMENTEN_ROOT}contactmomenten", + json=self.contactmoment, + status_code=201, + ), + m.post( + f"{CONTACTMOMENTEN_ROOT}klantcontactmomenten", + json=self.klant_contactmoment, + status_code=201, + ), + + def test_form_is_shown_if_open_klant_api_configured(self, m): + self._setUpMocks(m) + + self.assertTrue(self.ok_config.has_api_configuration()) + + response = self.app.get(self.case_detail_url, user=self.user) + contact_form = response.pyquery("#contact-form") + + self.assertTrue(response.context["case"]["contact_form_enabled"]) + self.assertTrue(contact_form) + + def test_form_is_shown_if_open_klant_email_configured(self, m): + self._setUpMocks(m) + + self.ok_config.register_email = "example@example.com" + self.ok_config.register_contact_moment = False + self.ok_config.save() + + self.assertFalse(self.ok_config.has_api_configuration()) + self.assertTrue(self.ok_config.has_register()) + + response = self.app.get(self.case_detail_url, user=self.user) + contact_form = response.pyquery("#contact-form") + + self.assertTrue(response.context["case"]["contact_form_enabled"]) + self.assertTrue(contact_form) + + def test_form_is_shown_if_open_klant_email_and_api_configured(self, m): self._setUpMocks(m) + self.ok_config.register_email = "example@example.com" + self.ok_config.save() + self.assertTrue(self.ok_config.has_api_configuration()) + self.assertTrue(self.ok_config.has_register()) response = self.app.get(self.case_detail_url, user=self.user) contact_form = response.pyquery("#contact-form") @@ -245,3 +305,76 @@ def test_no_form_shown_if_contact_form_disabled(self, m): self.assertFalse(response.context["case"]["contact_form_enabled"]) self.assertFalse(contact_form) + + def test_form_success_with_api(self, m): + self._setUpMocks(m) + self._setUpExtraMocks(m) + + response = self.app.get(self.case_detail_url, user=self.user) + form = response.forms["contact-form"] + form.action = reverse( + "cases:case_detail_contact_form", kwargs={"object_id": self.zaak["uuid"]} + ) + form["question"] = "Sample text" + response = form.submit() + + self.assertEqual( + response.headers["HX-Redirect"], + reverse("cases:case_detail", kwargs={"object_id": str(self.zaak["uuid"])}), + ) + + redirect = self.app.get(response.headers["HX-Redirect"]) + redirect_messages = list(redirect.context["messages"]) + + self.assertEqual(redirect_messages[0].message, _("Vraag verstuurd!")) + + def test_form_success_with_email(self, m): + self._setUpMocks(m) + self._setUpExtraMocks(m) + + self.ok_config.register_email = "example@example.com" + self.ok_config.register_contact_moment = False + self.ok_config.save() + + response = self.app.get(self.case_detail_url, user=self.user) + form = response.forms["contact-form"] + form.action = reverse( + "cases:case_detail_contact_form", kwargs={"object_id": self.zaak["uuid"]} + ) + form["question"] = "Sample text" + response = form.submit() + + self.assertEqual( + response.headers["HX-Redirect"], + reverse("cases:case_detail", kwargs={"object_id": str(self.zaak["uuid"])}), + ) + + redirect = self.app.get(response.headers["HX-Redirect"]) + redirect_messages = list(redirect.context["messages"]) + + self.assertEqual(redirect_messages[0].message, _("Vraag verstuurd!")) + + def test_form_success_with_both_email_and_api(self, m): + self._setUpMocks(m) + self._setUpExtraMocks(m) + + self.ok_config.register_email = "example@example.com" + self.ok_config.save() + + response = self.app.get(self.case_detail_url, user=self.user) + form = response.forms["contact-form"] + form.action = reverse( + "cases:case_detail_contact_form", kwargs={"object_id": self.zaak["uuid"]} + ) + form["question"] = "Sample text" + response = form.submit() + + self.assertEqual( + response.headers["HX-Redirect"], + reverse("cases:case_detail", kwargs={"object_id": str(self.zaak["uuid"])}), + ) + + redirect = self.app.get(response.headers["HX-Redirect"]) + redirect_messages = list(redirect.context["messages"]) + + self.assertEqual(redirect_messages[0].message, _("Vraag verstuurd!")) diff --git a/src/open_inwoner/cms/cases/views/status.py b/src/open_inwoner/cms/cases/views/status.py index ef15e99695..6555ca1ba5 100644 --- a/src/open_inwoner/cms/cases/views/status.py +++ b/src/open_inwoner/cms/cases/views/status.py @@ -5,8 +5,7 @@ from django.contrib import messages from django.core.exceptions import ObjectDoesNotExist, PermissionDenied from django.http import Http404, StreamingHttpResponse -from django.shortcuts import redirect -from django.urls import reverse, reverse_lazy +from django.urls import reverse from django.utils.functional import cached_property from django.utils.translation import gettext_lazy as _ from django.views import View @@ -14,6 +13,7 @@ from django_htmx.http import HttpResponseClientRedirect from glom import glom +from mail_editor.helpers import find_template from view_breadcrumbs import BaseBreadcrumbMixin from zgw_consumers.api_models.constants import RolOmschrijving @@ -203,7 +203,7 @@ def get_upload_info_context(self, case: Zaak): "external_upload_enabled": external_upload_enabled, "external_upload_url": external_upload_url, "contact_form_enabled": ( - contact_form_enabled and open_klant_config.has_api_configuration() + contact_form_enabled and open_klant_config.has_register() ), } @@ -414,11 +414,26 @@ class CaseContactFormView(CaseAccessMixin, CaseLogMixin, FormView): def post(self, request, *args, **kwargs): form = self.get_form() + if form.is_valid(): - form.cleaned_data[ - "question" - ] += f"\n\nCase number: {self.case.identificatie}" - return self.register_by_api(form) + config = OpenKlantConfig.get_solo() + + success = True + if config.register_email: + form.cleaned_data[ + "question" + ] += f"\n\nCase number: {self.case.identificatie}" + success = ( + self.register_by_email(form, config.register_email) and success + ) + if config.register_contact_moment: + success = self.register_by_api(form, config) and success + + self.get_result_message(success=success) + + return HttpResponseClientRedirect( + reverse("cases:case_detail", kwargs={"object_id": str(self.case.uuid)}) + ) else: return self.form_invalid(form) @@ -427,8 +442,52 @@ def get_success_url(self): "cases:case_detail_contact_form", kwargs={"object_id": str(self.case.uuid)} ) - def register_by_api(self, form): - config = OpenKlantConfig.get_solo() + def get_result_message(self, success=False): + if success: + return messages.add_message( + self.request, messages.SUCCESS, _("Vraag verstuurd!") + ) + else: + return messages.add_message( + self.request, + messages.ERROR, + _("Probleem bij versturen van de vraag."), + ) + + def register_by_email(self, form, recipient_email): + template = find_template("contactform_registration") + + context = { + "subject": _("Case: {case_identification}").format( + case_identification=self.case.identificatie + ), + "email": self.request.user.email, + "phonenumber": self.request.user.phonenumber, + "question": form.cleaned_data["question"], + } + + parts = [ + self.request.user.first_name, + self.request.user.infix if self.request.user.infix else "", + self.request.user.last_name, + ] + context["name"] = " ".join(p for p in parts) + + success = template.send_email([recipient_email], context) + + if success: + self.log_system_action( + "registered contactmoment by email", user=self.request.user + ) + return True + else: + self.log_system_action( + "error while registering contactmoment by email", + user=self.request.user, + ) + return False + + def register_by_api(self, form, config: OpenKlantConfig): assert config.has_api_configuration() klant = fetch_klant_for_bsn(self.request.user.bsn) @@ -475,17 +534,15 @@ def register_by_api(self, form): contactmoment = create_contactmoment(data, klant=klant) if contactmoment: - messages.add_message(self.request, messages.SUCCESS, _("Vraag verstuurd!")) - self.log_system_action(f"registered contactmoment by API") + self.log_system_action( + "registered contactmoment by API", user=self.request.user + ) + return True else: - messages.add_message( - self.request, messages.ERROR, _("Probleem bij versturen van de vraag.") + self.log_system_action( + "error while registering contactmoment by API", user=self.request.user ) - self.log_system_action(f"error while registering contactmoment by API") - - return HttpResponseClientRedirect( - reverse("cases:case_detail", kwargs={"object_id": str(self.case.uuid)}) - ) + return False def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) diff --git a/src/open_inwoner/openklant/models.py b/src/open_inwoner/openklant/models.py index 03d98691d3..99f46ca5e9 100644 --- a/src/open_inwoner/openklant/models.py +++ b/src/open_inwoner/openklant/models.py @@ -79,9 +79,11 @@ class OpenKlantConfig(SingletonModel): class Meta: verbose_name = _("Open Klant configuration") + def has_register(self) -> bool: + return self.register_email or self.has_api_configuration() + def has_form_configuration(self) -> bool: - has_register = self.register_email or self.has_api_configuration() - return has_register and self.contactformsubject_set.exists() + return self.has_register() and self.contactformsubject_set.exists() def has_api_configuration(self): return all(getattr(self, f, "") for f in self.register_api_required_fields) diff --git a/src/open_inwoner/scss/components/Cases/Cases.scss b/src/open_inwoner/scss/components/Cases/Cases.scss index e0aa282ea1..ffb5d9e17c 100644 --- a/src/open_inwoner/scss/components/Cases/Cases.scss +++ b/src/open_inwoner/scss/components/Cases/Cases.scss @@ -22,3 +22,7 @@ display: inline; } } + +#cases-contact-form-content > h2 { + margin-top: var(--spacing-large); +}