From 1024760c1569f1e285460b6b60992f52ab51285a Mon Sep 17 00:00:00 2001 From: Egor fureunoir Gorbunov Date: Tue, 1 Jul 2025 16:41:20 +0300 Subject: [PATCH] Features: 1) Add `autocomplete_list_filter` support in `Admin` classes; 2) Introduce `SkipVariableDoesNotExistFilter` to suppress specific log warnings. Fixes: 1) Clean up unused imports in `filters.py`. Extra: 1) Apply consistent string quoting across `admin.py` for formatting standardization; 2) Update logging configuration for `django.template` with new filter. --- core/admin.py | 46 ++++++++++++++++++++---------------- core/filters.py | 3 --- evibes/settings/logconfig.py | 22 +++++++++++++++++ 3 files changed, 48 insertions(+), 23 deletions(-) diff --git a/core/admin.py b/core/admin.py index f0531846..9b1eae95 100644 --- a/core/admin.py +++ b/core/admin.py @@ -117,10 +117,10 @@ class ActivationActionsMixin: class AjaxAutocompleteSelectWidget(AutocompleteSelect): def __init__(self, *args, **kwargs): - self.qs_target_value = kwargs.pop('qs_target_value') - self.model_admin = kwargs.pop('model_admin') - self.model = kwargs.pop('model') - self.field_name = kwargs.pop('field_name') + self.qs_target_value = kwargs.pop("qs_target_value") + self.model_admin = kwargs.pop("model_admin") + self.model = kwargs.pop("model") + self.field_name = kwargs.pop("field_name") kwargs.update(admin_site=self.model_admin.admin_site) kwargs.update(field=getattr(self.model, self.field_name).field) super().__init__(*args, **kwargs) @@ -128,14 +128,16 @@ class AjaxAutocompleteSelectWidget(AutocompleteSelect): def render(self, name, value, attrs=None, renderer=None): rendered = super().render(name, value, attrs, renderer) - return (f'
' - f'{rendered}
') + return ( + f'
' + f"{rendered}
" + ) class AjaxAutocompleteListFilter(RelatedFieldListFilter): - title = _('list filter') - parameter_name = '%s__%s__exact' - template = 'djaa_list_filter/admin/filter/autocomplete_list_filter.html' + title = _("list filter") + parameter_name = "%s__%s__exact" + template = "djaa_list_filter/admin/filter/autocomplete_list_filter.html" def __init__(self, field, request, params, model, model_admin, field_path): super().__init__(field, request, params, model, model_admin, field_path) @@ -177,22 +179,22 @@ class AjaxAutocompleteListFilterModelAdmin(ModelAdmin): return list_filter def get_autocomplete_list_filter(self): - return list(getattr(self, 'autocomplete_list_filter', [])) + return list(getattr(self, "autocomplete_list_filter", [])) class Media: js = [ - 'admin/js/vendor/jquery/jquery.js', - 'admin/js/vendor/select2/select2.full.js', - 'admin/js/vendor/select2/i18n/tr.js', - 'admin/js/jquery.init.js', - 'admin/js/autocomplete.js', - 'djaa_list_filter/admin/js/autocomplete_list_filter.js', + "admin/js/vendor/jquery/jquery.js", + "admin/js/vendor/select2/select2.full.js", + "admin/js/vendor/select2/i18n/tr.js", + "admin/js/jquery.init.js", + "admin/js/autocomplete.js", + "djaa_list_filter/admin/js/autocomplete_list_filter.js", ] css = { - 'screen': [ - 'admin/css/vendor/select2/select2.css', - 'admin/css/autocomplete.css', - 'djaa_list_filter/admin/css/autocomplete_list_filter.css', + "screen": [ + "admin/css/vendor/select2/select2.css", + "admin/css/autocomplete.css", + "djaa_list_filter/admin/css/autocomplete_list_filter.css", ] } @@ -327,6 +329,10 @@ class ProductAdmin(FieldsetsMixin, ActivationActionsMixin, AjaxAutocompleteListF "rating", "modified", ) + autocomplete_list_filter = ( + "category", + "brand", + ) list_filter = ( "is_active", "is_digital", diff --git a/core/filters.py b/core/filters.py index a79efa74..609aee41 100644 --- a/core/filters.py +++ b/core/filters.py @@ -2,7 +2,6 @@ import json import logging import uuid -from django.contrib.admin import SimpleListFilter from django.core.exceptions import BadRequest from django.db.models import ( Avg, @@ -17,9 +16,7 @@ from django.db.models import ( When, ) from django.db.models.functions import Coalesce -from django.urls import reverse from django.utils.http import urlsafe_base64_decode -from django.utils.safestring import mark_safe from django.utils.translation import gettext_lazy as _ from django_filters import ( BaseInFilter, diff --git a/evibes/settings/logconfig.py b/evibes/settings/logconfig.py index ab253eca..2a219f8f 100644 --- a/evibes/settings/logconfig.py +++ b/evibes/settings/logconfig.py @@ -1,5 +1,18 @@ from evibes.settings.base import * # noqa: F403 + +class SkipVariableDoesNotExistFilter(logging.Filter): # noqa: F405 + def filter(self, record: logging.LogRecord) -> bool: # noqa: F405 + if record.exc_info: + exc_type, exc_instance, _ = record.exc_info + try: + if exc_type.__name__ == "VariableDoesNotExist": # type: ignore + return False + except AttributeError: + return True + return "VariableDoesNotExist" not in record.getMessage() + + LOGGING = { "version": 1, "disable_existing_loggers": False, @@ -25,6 +38,9 @@ LOGGING = { "require_debug_true": { "()": "django.utils.log.RequireDebugTrue", }, + "skip_variable_doesnotexist": { + "()": "evibes.settings.logconfig.SkipVariableDoesNotExistFilter", + }, }, "handlers": { "console_debug": { @@ -61,6 +77,12 @@ LOGGING = { "level": "WARNING", "propagate": False, }, + "django.template": { + "handlers": ["console_debug", "console_production"], + "level": "DEBUG" if DEBUG else "INFO", # noqa: F405 + "propagate": True, + "filters": ["skip_variable_doesnotexist"], + }, "evibes": { "handlers": ["console_debug" if DEBUG else "console_production"], # noqa: F405 "level": "DEBUG" if DEBUG else "WARNING", # noqa: F405