aboutsummaryrefslogtreecommitdiffstats
path: root/pydis_site/apps
diff options
context:
space:
mode:
Diffstat (limited to 'pydis_site/apps')
-rw-r--r--pydis_site/apps/home/templatetags/wiki_extra.py72
-rw-r--r--pydis_site/apps/home/tests/test_wiki_templatetags.py231
-rw-r--r--pydis_site/apps/home/urls.py10
3 files changed, 310 insertions, 3 deletions
diff --git a/pydis_site/apps/home/templatetags/wiki_extra.py b/pydis_site/apps/home/templatetags/wiki_extra.py
new file mode 100644
index 00000000..289b0279
--- /dev/null
+++ b/pydis_site/apps/home/templatetags/wiki_extra.py
@@ -0,0 +1,72 @@
+from typing import Any, Dict, Type, Union
+
+from django import template
+from django.forms import BooleanField, BoundField, CharField, Field, ImageField, ModelChoiceField
+from django.template import Context
+from django.template.loader import get_template
+from django.utils.safestring import mark_safe
+from wiki.editors.markitup import MarkItUpWidget
+from wiki.forms import WikiSlugField
+from wiki.models import URLPath
+from wiki.plugins.notifications.forms import SettingsModelChoiceField
+
+TEMPLATE_PATH = "wiki/forms/fields/{0}.html"
+
+TEMPLATES: Dict[Type, str] = {
+ BooleanField: TEMPLATE_PATH.format("boolean"),
+ CharField: TEMPLATE_PATH.format("char"),
+ ImageField: TEMPLATE_PATH.format("image"),
+
+ ModelChoiceField: TEMPLATE_PATH.format("model_choice"),
+ SettingsModelChoiceField: TEMPLATE_PATH.format("model_choice"),
+ WikiSlugField: TEMPLATE_PATH.format("wiki_slug_render"),
+}
+
+
+register = template.Library()
+
+
+def get_unbound_field(field: Union[BoundField, Field]) -> Field:
+ while isinstance(field, BoundField):
+ field = field.field
+
+ return field
+
+
+def render(template_path: str, context: Dict[str, Any]):
+ return mark_safe(get_template(template_path).render(context)) # noqa: S703 S308
+
+
+def render_field(field: Field, render_labels: bool = True):
+ unbound_field = get_unbound_field(field)
+
+ if not isinstance(render_labels, bool):
+ render_labels = True
+
+ template_path = TEMPLATES.get(unbound_field.__class__, TEMPLATE_PATH.format("in_place_render"))
+ is_markitup = isinstance(unbound_field.widget, MarkItUpWidget)
+ context = {"field": field, "is_markitup": is_markitup, "render_labels": render_labels}
+
+ return render(template_path, context)
+
+
[email protected]_tag(takes_context=True)
+def get_field_options(context: Context, field: BoundField):
+ widget = field.field.widget
+
+ if field.value() is None:
+ value = []
+ else:
+ value = [str(field.value())]
+
+ context["options"] = widget.optgroups(field.name, value)
+ return ""
+
+
+def render_urlpath(value: Union[URLPath, str]):
+ if isinstance(value, str):
+ return value or "/"
+
+ return value.path or "/"
diff --git a/pydis_site/apps/home/tests/test_wiki_templatetags.py b/pydis_site/apps/home/tests/test_wiki_templatetags.py
new file mode 100644
index 00000000..201d3df4
--- /dev/null
+++ b/pydis_site/apps/home/tests/test_wiki_templatetags.py
@@ -0,0 +1,231 @@
+from unittest.mock import Mock, create_autospec
+
+from django.forms import (
+ BooleanField, BoundField, CharField, ChoiceField, Field, Form, ImageField,
+ ModelChoiceField
+)
+from django.template import Context, Template
+from django.test import TestCase
+from wiki.editors.markitup import MarkItUpWidget
+from wiki.forms import WikiSlugField
+from wiki.models import Article, URLPath as _URLPath
+from wiki.plugins.notifications.forms import SettingsModelChoiceField
+
+from pydis_site.apps.home.templatetags import wiki_extra
+
+URLPath = Mock(_URLPath)
+
+
+class TestURLPathFilter(TestCase):
+ TEMPLATE = Template(
+ """
+ {% load wiki_extra %}
+ {{ obj|render_urlpath }}
+ """
+ )
+
+ def test_str(self):
+ context = {"obj": "/path/"}
+ rendered = self.TEMPLATE.render(Context(context))
+
+ self.assertEqual(rendered.strip(), "/path/")
+
+ def test_str_empty(self):
+ context = {"obj": ""}
+ rendered = self.TEMPLATE.render(Context(context))
+
+ self.assertEqual(rendered.strip(), "/")
+
+ def test_urlpath(self):
+ url_path = URLPath()
+ url_path.path = "/path/"
+
+ context = {"obj": url_path}
+ rendered = self.TEMPLATE.render(Context(context))
+
+ self.assertEqual(rendered.strip(), "/path/")
+
+ def test_urlpath_root(self):
+ url_path = URLPath()
+ url_path.path = None
+
+ context = {"obj": url_path}
+ rendered = self.TEMPLATE.render(Context(context))
+
+ self.assertEqual(rendered.strip(), "/")
+
+
+class TestRenderField(TestCase):
+ TEMPLATE = Template(
+ """
+ {% load wiki_extra %}
+ {% render_field field %}
+ """
+ )
+
+ TEMPLATE_NO_LABELS = Template(
+ """
+ {% load wiki_extra %}
+ {% render_field field render_labels=False %}
+ """
+ )
+
+ TEMPLATE_LABELS_NOT_BOOLEAN = Template(
+ """
+ {% load wiki_extra %}
+ {% render_field field render_labels="" %}
+ """
+ )
+
+ def test_bound_field(self):
+ unbound_field = Field()
+ field = BoundField(Form(), unbound_field, "field")
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ def test_bound_field_no_labels(self):
+ unbound_field = Field()
+ field = BoundField(Form(), unbound_field, "field")
+
+ context = Context({"field": field})
+ self.TEMPLATE_NO_LABELS.render(context)
+
+ def test_bound_field_labels_not_boolean(self):
+ unbound_field = Field()
+ field = BoundField(Form(), unbound_field, "field")
+
+ context = Context({"field": field})
+ self.TEMPLATE_LABELS_NOT_BOOLEAN.render(context)
+
+ def test_unbound_field(self):
+ field = Field()
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ def test_unbound_field_no_labels(self):
+ field = Field()
+
+ context = Context({"field": field})
+ self.TEMPLATE_NO_LABELS.render(context)
+
+ def test_unbound_field_labels_not_boolean(self):
+ field = Field()
+
+ context = Context({"field": field})
+ self.TEMPLATE_LABELS_NOT_BOOLEAN.render(context)
+
+
+class TestRenderFieldTypes(TestCase):
+ TEMPLATE = Template(
+ """
+ {% load wiki_extra %}
+ {% render_field field %}
+ """
+ )
+
+ @classmethod
+ def setUpClass(cls):
+ cls._wiki_extra_render = wiki_extra.render
+ wiki_extra.render = create_autospec(wiki_extra.render, return_value="")
+
+ @classmethod
+ def tearDownClass(cls):
+ wiki_extra.render = cls._wiki_extra_render
+ del cls._wiki_extra_render
+
+ def test_field_boolean(self):
+ field = BooleanField()
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/boolean.html"
+ context = {"field": field, "is_markitup": False, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+ def test_field_char(self):
+ field = CharField()
+ field.widget = None
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/char.html"
+ context = {"field": field, "is_markitup": False, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+ def test_field_char_markitup(self):
+ field = CharField()
+ field.widget = MarkItUpWidget()
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/char.html"
+ context = {"field": field, "is_markitup": True, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+ def test_field_image(self):
+ field = ImageField()
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/image.html"
+ context = {"field": field, "is_markitup": False, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+ def test_field_model_choice(self):
+ field = ModelChoiceField(Article.objects.all())
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/model_choice.html"
+ context = {"field": field, "is_markitup": False, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+ def test_field_settings_model_choice(self):
+ field = SettingsModelChoiceField(Article.objects.all())
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/model_choice.html"
+ context = {"field": field, "is_markitup": False, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+ def test_field_wiki_slug(self):
+ field = WikiSlugField()
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
+
+ template_path = "wiki/forms/fields/wiki_slug_render.html"
+ context = {"field": field, "is_markitup": False, "render_labels": True}
+
+ wiki_extra.render.assert_called_with(template_path, context)
+
+
+class TestGetFieldOptions(TestCase):
+ TEMPLATE = Template(
+ """
+ {% load wiki_extra %}
+ {% get_field_options field %}
+ """
+ )
+
+ def test_get_field_options(self):
+ unbound_field = ChoiceField()
+ field = BoundField(Form(), unbound_field, "field")
+
+ context = Context({"field": field})
+ self.TEMPLATE.render(context)
diff --git a/pydis_site/apps/home/urls.py b/pydis_site/apps/home/urls.py
index d8dba2f6..b22508d9 100644
--- a/pydis_site/apps/home/urls.py
+++ b/pydis_site/apps/home/urls.py
@@ -1,10 +1,14 @@
+from django.conf import settings
+from django.conf.urls.static import static
from django.contrib import admin
-from django.urls import path
+from django.urls import include, path
from .views import HomeView
app_name = 'home'
urlpatterns = [
path('', HomeView.as_view(), name='home'),
- path('admin/', admin.site.urls)
-]
+ path('admin/', admin.site.urls),
+ path('notifications/', include('django_nyt.urls')),
+ path('wiki/', include('wiki.urls')),
+] + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)