From 89032988184a49cd6a9f3db3903fcf25b61ec159 Mon Sep 17 00:00:00 2001
From: Emmanuel Cazenave <ecazenave@entrouvert.com>
Date: Wed, 11 May 2022 18:38:48 +0200
Subject: [PATCH] maintenance: allow a custom message on the maintenance page
 (#65143)

---
 hobo/maintenance/forms.py      | 6 ++++++
 hobo/maintenance/views.py      | 8 ++++++++
 hobo/middleware/maintenance.py | 4 +++-
 tests/test_maintenance.py      | 5 +++++
 4 files changed, 22 insertions(+), 1 deletion(-)

diff --git a/hobo/maintenance/forms.py b/hobo/maintenance/forms.py
index 1352a76..df4a173 100644
--- a/hobo/maintenance/forms.py
+++ b/hobo/maintenance/forms.py
@@ -20,6 +20,12 @@ from django.utils.translation import ugettext_lazy as _
 
 class MaintenanceForm(forms.Form):
     maintenance_page = forms.BooleanField(required=False, label=_('Enable maintenance page'))
+    maintenance_page_message = forms.CharField(
+        required=False,
+        widget=forms.Textarea,
+        label=_('Maintenance page message'),
+        help_text=_('The default value is: "The site is under maintenance."'),
+    )
     maintenance_pass_trough_header = forms.CharField(
         required=False, label=_('Maintenance HTTP header pass through')
     )
diff --git a/hobo/maintenance/views.py b/hobo/maintenance/views.py
index 8ff5117..4d4ab5c 100644
--- a/hobo/maintenance/views.py
+++ b/hobo/maintenance/views.py
@@ -33,6 +33,10 @@ class HomeView(FormView):
     def maintenance_page_variable(self):
         return get_setting_variable('MAINTENANCE_PAGE')
 
+    @cached_property
+    def maintenance_page_message_variable(self):
+        return get_setting_variable('MAINTENANCE_PAGE_MESSAGE')
+
     @cached_property
     def maintenance_pass_trough_header_variable(self):
         return get_setting_variable('MAINTENANCE_PASS_THROUGH_HEADER')
@@ -44,6 +48,7 @@ class HomeView(FormView):
     def get_initial(self):
         initial = super().get_initial()
         initial['maintenance_page'] = bool(self.maintenance_page_variable.json)
+        initial['maintenance_page_message'] = self.maintenance_page_message_variable.value
         initial['maintenance_pass_trough_header'] = self.maintenance_pass_trough_header_variable.value
         initial['disable_cron'] = bool(self.tenant_disable_cron_jobs_variable.json)
         return initial
@@ -51,6 +56,9 @@ class HomeView(FormView):
     def form_valid(self, form):
         self.maintenance_page_variable.json = form.cleaned_data['maintenance_page']
         self.maintenance_page_variable.save()
+        self.maintenance_page_message_variable.value = form.cleaned_data['maintenance_page_message']
+        self.maintenance_page_message_variable.save()
+
         self.maintenance_pass_trough_header_variable.value = form.cleaned_data[
             'maintenance_pass_trough_header'
         ]
diff --git a/hobo/middleware/maintenance.py b/hobo/middleware/maintenance.py
index f9c9ebe..3b14151 100644
--- a/hobo/middleware/maintenance.py
+++ b/hobo/middleware/maintenance.py
@@ -38,7 +38,9 @@ class MaintenanceMiddleware:
     def __call__(self, request):
         maintenance_mode = getattr(settings, 'MAINTENANCE_PAGE', None)
         if maintenance_mode and not pass_through(request):
-            maintenance_msg = _('The site is under maintenance')
+            maintenance_msg = getattr(settings, 'MAINTENANCE_PAGE_MESSAGE', '')
+            if not maintenance_msg:
+                maintenance_msg = _('The site is under maintenance.')
             context = {'maintenance_msg': maintenance_msg}
             return TemplateResponse(
                 request, 'hobo/maintenance/maintenance_page.html', context=context, status=503
diff --git a/tests/test_maintenance.py b/tests/test_maintenance.py
index 04aac20..6207125 100644
--- a/tests/test_maintenance.py
+++ b/tests/test_maintenance.py
@@ -27,6 +27,7 @@ def test_maintenance_middleware(app, admin_user, db, monkeypatch, settings):
 
 def test_manage(app, admin_user, settings):
     assert Variable.objects.filter(name='SETTING_MAINTENANCE_PAGE').count() == 0
+    assert Variable.objects.filter(name='SETTING_MAINTENANCE_MESSAGE').count() == 0
     assert Variable.objects.filter(name='SETTING_MAINTENANCE_PASS_THROUGH_HEADER').count() == 0
     assert Variable.objects.filter(name='TENANT_DISABLE_CRON_JOBS').count() == 0
     assert not getattr(settings, 'MAINTENANCE_PASS_THROUGH_IPS', [])
@@ -35,20 +36,24 @@ def test_manage(app, admin_user, settings):
     resp = app.get('/maintenance/')
     assert 'No IP addresses configured' in resp.text
     resp.form.set('maintenance_page', True)
+    resp.form.set('maintenance_page_message', 'Foo')
     resp.form.set('maintenance_pass_trough_header', 'X-Entrouvert')
     resp.form.set('disable_cron', True)
     resp = resp.form.submit().follow()
     assert Variable.objects.filter(name='SETTING_MAINTENANCE_PAGE').get().value == 'true'
+    assert Variable.objects.filter(name='SETTING_MAINTENANCE_PAGE_MESSAGE').get().value == 'Foo'
     assert (
         Variable.objects.filter(name='SETTING_MAINTENANCE_PASS_THROUGH_HEADER').get().value == 'X-Entrouvert'
     )
     assert Variable.objects.filter(name='SETTING_TENANT_DISABLE_CRON_JOBS').get().value == 'true'
 
     resp.form.set('maintenance_page', False)
+    resp.form.set('maintenance_page_message', '')
     resp.form.set('maintenance_pass_trough_header', '')
     resp.form.set('disable_cron', False)
     resp = resp.form.submit().follow()
     assert Variable.objects.filter(name='SETTING_MAINTENANCE_PAGE').get().value == 'false'
+    assert Variable.objects.filter(name='SETTING_MAINTENANCE_PAGE_MESSAGE').get().value == ''
     assert Variable.objects.filter(name='SETTING_MAINTENANCE_PASS_THROUGH_HEADER').get().value == ''
     assert Variable.objects.filter(name='SETTING_TENANT_DISABLE_CRON_JOBS').get().value == 'false'
 
-- 
2.30.2

