diff --git a/passbook/admin/tests.py b/passbook/admin/tests.py new file mode 100644 index 000000000..efc8ee6b3 --- /dev/null +++ b/passbook/admin/tests.py @@ -0,0 +1,37 @@ +"""admin tests""" +from typing import Callable + +from django.shortcuts import reverse +from django.test import Client, TestCase +from django.urls.exceptions import NoReverseMatch + +from passbook.admin.urls import urlpatterns +from passbook.core.models import User + + +class TestAdmin(TestCase): + """Generic admin tests""" + + def setUp(self): + self.user = User.objects.create_superuser(username="test") + self.client = Client() + self.client.force_login(self.user) + + +def generic_view_tester(view_name: str) -> Callable: + """This is used instead of subTest for better visibility""" + + def tester(self: TestAdmin): + try: + full_url = reverse(f"passbook_admin:{view_name}") + response = self.client.get(full_url) + self.assertTrue(response.status_code < 500) + except NoReverseMatch: + pass + + return tester + + +for url in urlpatterns: + method_name = url.name.replace("-", "_") + setattr(TestAdmin, f"test_{method_name}", generic_view_tester(url.name)) diff --git a/passbook/admin/views/policies.py b/passbook/admin/views/policies.py index f1a835b06..4c1a441c2 100644 --- a/passbook/admin/views/policies.py +++ b/passbook/admin/views/policies.py @@ -62,9 +62,10 @@ class PolicyCreateView( def get_form_class(self): policy_type = self.request.GET.get("type") - model = next(x for x in all_subclasses(Policy) if x.__name__ == policy_type) - if not model: - raise Http404 + try: + model = next(x for x in all_subclasses(Policy) if x.__name__ == policy_type) + except StopIteration as exc: + raise Http404 from exc return path_to_class(model.form) diff --git a/passbook/admin/views/property_mapping.py b/passbook/admin/views/property_mapping.py index 426e06dd4..1de9bfe04 100644 --- a/passbook/admin/views/property_mapping.py +++ b/passbook/admin/views/property_mapping.py @@ -53,11 +53,14 @@ class PropertyMappingCreateView( def get_context_data(self, **kwargs): kwargs = super().get_context_data(**kwargs) property_mapping_type = self.request.GET.get("type") - model = next( - x - for x in all_subclasses(PropertyMapping) - if x.__name__ == property_mapping_type - ) + try: + model = next( + x + for x in all_subclasses(PropertyMapping) + if x.__name__ == property_mapping_type + ) + except StopIteration as exc: + raise Http404 from exc kwargs["type"] = model._meta.verbose_name form_cls = self.get_form_class() if hasattr(form_cls, "template_name"): @@ -66,13 +69,14 @@ class PropertyMappingCreateView( def get_form_class(self): property_mapping_type = self.request.GET.get("type") - model = next( - x - for x in all_subclasses(PropertyMapping) - if x.__name__ == property_mapping_type - ) - if not model: - raise Http404 + try: + model = next( + x + for x in all_subclasses(PropertyMapping) + if x.__name__ == property_mapping_type + ) + except StopIteration as exc: + raise Http404 from exc return path_to_class(model.form) diff --git a/passbook/admin/views/providers.py b/passbook/admin/views/providers.py index f0a1d5892..ff1c96ebe 100644 --- a/passbook/admin/views/providers.py +++ b/passbook/admin/views/providers.py @@ -52,9 +52,12 @@ class ProviderCreateView( def get_form_class(self): provider_type = self.request.GET.get("type") - model = next(x for x in all_subclasses(Provider) if x.__name__ == provider_type) - if not model: - raise Http404 + try: + model = next( + x for x in all_subclasses(Provider) if x.__name__ == provider_type + ) + except StopIteration as exc: + raise Http404 from exc return path_to_class(model.form) diff --git a/passbook/admin/views/sources.py b/passbook/admin/views/sources.py index b5d46af2f..2c979c043 100644 --- a/passbook/admin/views/sources.py +++ b/passbook/admin/views/sources.py @@ -52,9 +52,10 @@ class SourceCreateView( def get_form_class(self): source_type = self.request.GET.get("type") - model = next(x for x in all_subclasses(Source) if x.__name__ == source_type) - if not model: - raise Http404 + try: + model = next(x for x in all_subclasses(Source) if x.__name__ == source_type) + except StopIteration as exc: + raise Http404 from exc return path_to_class(model.form) diff --git a/passbook/admin/views/stages.py b/passbook/admin/views/stages.py index c2c86d2be..311923210 100644 --- a/passbook/admin/views/stages.py +++ b/passbook/admin/views/stages.py @@ -59,9 +59,10 @@ class StageCreateView( def get_form_class(self): stage_type = self.request.GET.get("type") - model = next(x for x in all_subclasses(Stage) if x.__name__ == stage_type) - if not model: - raise Http404 + try: + model = next(x for x in all_subclasses(Stage) if x.__name__ == stage_type) + except StopIteration as exc: + raise Http404 from exc return path_to_class(model.form) diff --git a/scripts/pre-commit.sh b/scripts/pre-commit.sh index 2960f8976..1cf64708d 100755 --- a/scripts/pre-commit.sh +++ b/scripts/pre-commit.sh @@ -2,8 +2,8 @@ isort -rc passbook pyright black passbook +./manage.py generate_swagger -o swagger.yaml -f yaml scripts/coverage.sh bandit -r passbook pylint passbook prospector -./manage.py generate_swagger -o swagger.yaml -f yaml