Filtro predefinito nell'amministratore di Django


94

Come posso modificare la scelta del filtro predefinito da "TUTTI"? Ho un campo denominato come statusche ha tre valori: activate, pendinge rejected. Quando lo uso list_filternell'amministratore di Django, il filtro è impostato per impostazione predefinita su "Tutti" ma voglio impostarlo in sospeso per impostazione predefinita.

Risposte:


102

Per ottenere ciò e avere un collegamento "Tutto" utilizzabile nella barra laterale (ovvero uno che mostra tutto anziché mostrare in sospeso), è necessario creare un filtro elenco personalizzato, ereditando django.contrib.admin.filters.SimpleListFiltere filtrando su "in sospeso" per impostazione predefinita. Qualcosa del genere dovrebbe funzionare:

from datetime import date

from django.utils.translation import ugettext_lazy as _
from django.contrib.admin import SimpleListFilter

class StatusFilter(SimpleListFilter):
    title = _('Status')

    parameter_name = 'status'

    def lookups(self, request, model_admin):
        return (
            (None, _('Pending')),
            ('activate', _('Activate')),
            ('rejected', _('Rejected')),
            ('all', _('All')),
        )

    def choices(self, cl):
        for lookup, title in self.lookup_choices:
            yield {
                'selected': self.value() == lookup,
                'query_string': cl.get_query_string({
                    self.parameter_name: lookup,
                }, []),
                'display': title,
            }

    def queryset(self, request, queryset):
        if self.value() in ('activate', 'rejected'):
            return queryset.filter(status=self.value())    
        elif self.value() == None:
            return queryset.filter(status='pending')


class Admin(admin.ModelAdmin): 
    list_filter = [StatusFilter] 

EDIT: richiede Django 1.4 (grazie Simon)


3
Questa è la soluzione più pulita di tutte, ma ha il minor numero di voti positivi ... richiede Django 1.4, anche se dovrebbe essere un dato di fatto ormai.
Simon

@Greg Come rimuovi completamente la funzionalità del filtro e la scheda del filtro dalla pagina di amministrazione?


2
Questa soluzione presenta un piccolo inconveniente. Quando i filtri sono vuoti (effettivamente utilizzato il filtro "in sospeso"), Django 1.8 determina erroneamente il conteggio completo dei risultati e non mostra il conteggio dei risultati se show_full_result_count è True (per impostazione predefinita). -
Alexander Fedotov

Si noti che se non si riesce a sovrascrivere il choicesmetodo nella soluzione, continuerà fastidiosamente ad aggiungere la propria opzione Tutto all'inizio dell'elenco di scelte.
richard

47
class MyModelAdmin(admin.ModelAdmin):   

    def changelist_view(self, request, extra_context=None):

        if not request.GET.has_key('decommissioned__exact'):

            q = request.GET.copy()
            q['decommissioned__exact'] = 'N'
            request.GET = q
            request.META['QUERY_STRING'] = request.GET.urlencode()
        return super(MyModelAdmin,self).changelist_view(request, extra_context=extra_context)

18
Questa soluzione ha lo svantaggio che sebbene la scelta "Tutti" sia ancora visualizzata nell'interfaccia utente, selezionandola applica comunque il filtro predefinito.
akaihola

ho la stessa domanda, ma posso capire il replay ... scusa sono nuovo con Django ... ma forse questo funzionerà blog.dougalmatthews.com/2008/10/…
Asinox

Questo va bene, ma avevo bisogno di vedere il parametro get nell'URL in modo che il mio filtro possa raccoglierlo e mostrarlo selezionato. Pubblicando la mia soluzione a breve.
radtek

spiegazione mancante. postare solo un pezzo di codice potrebbe non aiutare tutti. Inoltre non funziona e senza un po 'di contesto è difficile scoprire perché
EvilSmurf,

19

Ha preso la risposta di ha22109 sopra e modificato per consentire la selezione di "Tutti" confrontando HTTP_REFERERe PATH_INFO.

class MyModelAdmin(admin.ModelAdmin):

    def changelist_view(self, request, extra_context=None):

        test = request.META['HTTP_REFERER'].split(request.META['PATH_INFO'])

        if test[-1] and not test[-1].startswith('?'):
            if not request.GET.has_key('decommissioned__exact'):

                q = request.GET.copy()
                q['decommissioned__exact'] = 'N'
                request.GET = q
                request.META['QUERY_STRING'] = request.GET.urlencode()
        return super(MyModelAdmin,self).changelist_view(request, extra_context=extra_context)

3
Questo ha rotto per me perché HTTP_REFERER non era sempre presente. Ho fatto 'referer = request.META.get (' HTTP_REFERER ',' '); test = referer.split (request.META ['PATH_INFO']) `
ben autore

@ Ben sto usando le tue due linee referer = request.META.get ('HTTP_REFERER', '') test = referer.split (request.META ['PATH_INFO']). Non mi interessa molto di HTTP_REFERER. Il problema viene risolto completamente da queste righe se HTTP_REFERER non è presente.
the_game

@ the_game sì, l'idea è che se usi le parentesi quadre per tentare di accedere a una chiave che non esiste, viene KeyErrorlanciata, mentre se usi il get()metodo di dict puoi specificare un valore predefinito. Ho specificato un valore predefinito di stringa vuota in modo che split () non generi AttributeError. È tutto.
ben autore

@ Ben. Grazie per me funziona. Puoi anche rispondere a questa domanda, credo che questa sia un'estensione a questa domanda solo su stackoverflow.com/questions/10410982/… . Puoi per favore fornirmi una soluzione per questo.
the_game

1
Funziona bene. has_key()è sconsigliato a favore di key in d. Ma so che hai appena preso dalla risposta di ha22109. Una domanda: perché usare request.META['PATH_INFO']quando potresti semplicemente usare request.path_info(più breve)?
Nick il

19

So che questa domanda è piuttosto vecchia ora, ma è ancora valida. Credo che questo sia il modo più corretto per farlo. È essenzialmente lo stesso del metodo di Greg, ma formulato come una classe estendibile per un facile riutilizzo.

from django.contrib.admin import SimpleListFilter
from django.utils.encoding import force_text
from django.utils.translation import ugettext as _

class DefaultListFilter(SimpleListFilter):
    all_value = '_all'

    def default_value(self):
        raise NotImplementedError()

    def queryset(self, request, queryset):
        if self.parameter_name in request.GET and request.GET[self.parameter_name] == self.all_value:
            return queryset

        if self.parameter_name in request.GET:
            return queryset.filter(**{self.parameter_name:request.GET[self.parameter_name]})

        return queryset.filter(**{self.parameter_name:self.default_value()})

    def choices(self, cl):
        yield {
            'selected': self.value() == self.all_value,
            'query_string': cl.get_query_string({self.parameter_name: self.all_value}, []),
            'display': _('All'),
        }
        for lookup, title in self.lookup_choices:
            yield {
                'selected': self.value() == force_text(lookup) or (self.value() == None and force_text(self.default_value()) == force_text(lookup)),
                'query_string': cl.get_query_string({
                    self.parameter_name: lookup,
                }, []),
                'display': title,
            }

class StatusFilter(DefaultListFilter):
    title = _('Status ')
    parameter_name = 'status__exact'

    def lookups(self, request, model_admin):
        return ((0,'activate'), (1,'pending'), (2,'rejected'))

    def default_value(self):
        return 1

class MyModelAdmin(admin.ModelAdmin):
    list_filter = (StatusFilter,)

8

Ecco la mia soluzione generica che utilizza il reindirizzamento, controlla solo se ci sono parametri GET, se non ne esistono, reindirizza con il parametro get predefinito. Ho anche un set list_filter in modo che lo raccolga e visualizzi il valore predefinito.

from django.shortcuts import redirect

class MyModelAdmin(admin.ModelAdmin):   

    ...

    list_filter = ('status', )

    def changelist_view(self, request, extra_context=None):
        referrer = request.META.get('HTTP_REFERER', '')
        get_param = "status__exact=5"
        if len(request.GET) == 0 and '?' not in referrer:
            return redirect("{url}?{get_parms}".format(url=request.path, get_parms=get_param))
        return super(MyModelAdmin,self).changelist_view(request, extra_context=extra_context)

L'unico avvertimento è quando accedi direttamente alla pagina con "?" presente nell'URL, non è impostato alcun HTTP_REFERER, quindi utilizzerà il parametro predefinito e il reindirizzamento. Per me va bene, funziona benissimo quando fai clic sul filtro dell'amministratore.

AGGIORNAMENTO :

Per aggirare l'avvertenza, ho finito per scrivere una funzione di filtro personalizzata che semplificava la funzionalità changelist_view. Ecco il filtro:

class MyModelStatusFilter(admin.SimpleListFilter):
    title = _('Status')
    parameter_name = 'status'

    def lookups(self, request, model_admin):  # Available Values / Status Codes etc..
        return (
            (8, _('All')),
            (0, _('Incomplete')),
            (5, _('Pending')),
            (6, _('Selected')),
            (7, _('Accepted')),
        )

    def choices(self, cl):  # Overwrite this method to prevent the default "All"
        from django.utils.encoding import force_text
        for lookup, title in self.lookup_choices:
            yield {
                'selected': self.value() == force_text(lookup),
                'query_string': cl.get_query_string({
                    self.parameter_name: lookup,
                }, []),
                'display': title,
            }

    def queryset(self, request, queryset):  # Run the queryset based on your lookup values
        if self.value() is None:
            return queryset.filter(status=5)
        elif int(self.value()) == 0:
            return queryset.filter(status__lte=4)
        elif int(self.value()) == 8:
            return queryset.all()
        elif int(self.value()) >= 5:
            return queryset.filter(status=self.value())
        return queryset.filter(status=5)

E changelist_view ora passa solo il parametro predefinito se non ce ne sono. L'idea era di eliminare la capacità dei filtri generici di visualizzare tutto senza utilizzare parametri get. Per visualizzare tutto ho assegnato lo stato = 8 a tale scopo:

class MyModelAdmin(admin.ModelAdmin):   

    ...

    list_filter = ('status', )

    def changelist_view(self, request, extra_context=None):
        if len(request.GET) == 0:
            get_param = "status=5"
            return redirect("{url}?{get_parms}".format(url=request.path, get_parms=get_param))
        return super(MyModelAdmin, self).changelist_view(request, extra_context=extra_context)

Ho una correzione per il mio avvertimento, un filtro personalizzato. Lo presenterò come una soluzione alternativa.
Radtek

Grazie, trovo che il reindirizzamento sia la soluzione più pulita e semplice. Inoltre non capisco "l'avvertenza". Ottengo sempre il risultato desiderato, facendo clic o utilizzando il collegamento diretto (non ho utilizzato il filtro personalizzato).
Dennis Golomazov

6
def changelist_view( self, request, extra_context = None ):
    default_filter = False
    try:
        ref = request.META['HTTP_REFERER']
        pinfo = request.META['PATH_INFO']
        qstr = ref.split( pinfo )

        if len( qstr ) < 2:
            default_filter = True
    except:
        default_filter = True

    if default_filter:
        q = request.GET.copy()
        q['registered__exact'] = '1'
        request.GET = q
        request.META['QUERY_STRING'] = request.GET.urlencode()

    return super( InterestAdmin, self ).changelist_view( request, extra_context = extra_context )

4

Si può semplicemente utilizzare return queryset.filter()o if self.value() is Nonee il metodo di SimpleListFilter Override

from django.utils.encoding import force_text

def choices(self, changelist):
    for lookup, title in self.lookup_choices:
        yield {
            'selected': force_text(self.value()) == force_text(lookup),
            'query_string': changelist.get_query_string(
                {self.parameter_name: lookup}, []
            ),
            'display': title,
        }

3

Tieni presente che se invece di preselezionare un valore di filtro desideri sempre pre-filtrare i dati prima di visualizzarli nell'amministratore, devi ModelAdmin.queryset()invece sostituire il metodo.


Questa è una soluzione abbastanza pulita e veloce anche se potrebbe comunque causare problemi. Quando le opzioni di filtro sono abilitate nell'amministratore, l'utente potrebbe ottenere risultati apparentemente errati. Se il set di query sostituito contiene una clausola .exclude (), i record rilevati da tale non verranno mai elencati, ma le opzioni di filtro dell'amministratore per mostrarli esplicitamente saranno comunque offerte dall'interfaccia utente dell'amministratore.
Tomas Andrle

Ci sono altre risposte più corrette con voti inferiori che si applicano a questa situazione poiché l'OP ha chiaramente chiesto di inserire un filtro in cui un set di query sarebbe la soluzione sbagliata, come indicato anche da @TomasAndrle sopra.
eskhool

Grazie per averlo sottolineato @eskhool, ho provato a downvote la mia risposta a zero ma sembra che non sia permesso di downvote se stessi.
akaihola

3

Un leggero miglioramento rispetto alla risposta di Greg utilizzando DjangoChoices, Python> = 2.5 e ovviamente Django> = 1.4.

from django.utils.translation import ugettext_lazy as _
from django.contrib.admin import SimpleListFilter

class OrderStatusFilter(SimpleListFilter):
    title = _('Status')

    parameter_name = 'status__exact'
    default_status = OrderStatuses.closed

    def lookups(self, request, model_admin):
        return (('all', _('All')),) + OrderStatuses.choices

    def choices(self, cl):
        for lookup, title in self.lookup_choices:
            yield {
                'selected': self.value() == lookup if self.value() else lookup == self.default_status,
                'query_string': cl.get_query_string({self.parameter_name: lookup}, []),
                'display': title,
            }

    def queryset(self, request, queryset):
        if self.value() in OrderStatuses.values:
            return queryset.filter(status=self.value())
        elif self.value() is None:
            return queryset.filter(status=self.default_status)


class Admin(admin.ModelAdmin):
    list_filter = [OrderStatusFilter] 

Grazie a Greg per la bella soluzione!


2

So che non è la soluzione migliore, ma ho cambiato index.html nel modello di amministrazione, riga 25 e 37 in questo modo:

25: <th scope="row"><a href="{{ model.admin_url }}{% ifequal model.name "yourmodelname" %}?yourflag_flag__exact=1{% endifequal %}">{{ model.name }}</a></th>

37: <td><a href="{{ model.admin_url }}{% ifequal model.name "yourmodelname" %}?yourflag__exact=1{% endifequal %}" class="changelink">{% trans 'Change' %}</a></td>


1

Ho dovuto apportare una modifica per far funzionare correttamente il filtro. La soluzione precedente ha funzionato per me quando la pagina è stata caricata. Se è stata eseguita una "azione", il filtro tornava a "Tutti" e non a quello predefinito. Questa soluzione carica la pagina di modifica dell'amministratore con il filtro predefinito, ma mantiene anche le modifiche del filtro o il filtro corrente quando si verificano altre attività sulla pagina. Non ho testato tutti i casi, ma in realtà potrebbe limitare l'impostazione di un filtro predefinito che si verifica solo quando la pagina viene caricata.

def changelist_view(self, request, extra_context=None):
    default_filter = False

    try:
        ref = request.META['HTTP_REFERER']
        pinfo = request.META['PATH_INFO']
        qstr = ref.split(pinfo)
        querystr = request.META['QUERY_STRING']

        # Check the QUERY_STRING value, otherwise when
        # trying to filter the filter gets reset below
        if querystr is None:
            if len(qstr) < 2 or qstr[1] == '':
                default_filter = True
    except:
        default_filter = True

    if default_filter:
        q = request.GET.copy()
        q['registered__isnull'] = 'True'
        request.GET = q
        request.META['QUERY_STRING'] = request.GET.urlencode()

    return super(MyAdmin, self).changelist_view(request, extra_context=extra_context)

1

Un po 'fuori tema ma la mia ricerca di una domanda simile mi ha portato qui. Stavo cercando di avere una query predefinita per una data (cioè se non viene fornito alcun input, mostra solo gli oggetti con timestamp"Oggi"), il che complica un po 'la domanda. Ecco cosa mi è venuto in mente:

from django.contrib.admin.options import IncorrectLookupParameters
from django.core.exceptions import ValidationError

class TodayDefaultDateFieldListFilter(admin.DateFieldListFilter):
    """ If no date is query params are provided, query for Today """

    def queryset(self, request, queryset):
        try:
            if not self.used_parameters:
                now = datetime.datetime.now().replace(hour=0, minute=0, second=0, microsecond=0)
                self.used_parameters = {
                    ('%s__lt' % self.field_path): str(now + datetime.timedelta(days=1)),
                    ('%s__gte' % self.field_path): str(now),
                }
                # Insure that the dropdown reflects 'Today'
                self.date_params = self.used_parameters
            return queryset.filter(**self.used_parameters)
        except ValidationError, e:
            raise IncorrectLookupParameters(e)

class ImagesAdmin(admin.ModelAdmin):
    list_filter = (
        ('timestamp', TodayDefaultDateFieldListFilter),
    )

Questa è una semplice sostituzione del valore predefinito DateFieldListFilter. Impostando self.date_params, assicura che il menu a discesa del filtro si aggiorni a qualsiasi opzione corrisponda a self.used_parameters. Per questo motivo, è necessario assicurarsi che self.used_parameterssiano esattamente ciò che verrebbe utilizzato da una di quelle selezioni a discesa (ad esempio, scoprire quale date_paramssarebbe quando si utilizza "Oggi" o "Ultimi 7 giorni" e costruire il self.used_parametersper abbinarli).

Questo è stato creato per funzionare con Django 1.4.10


1

Potrebbe essere un vecchio thread, ma ho pensato di aggiungere la mia soluzione perché non riuscivo a trovare risposte migliori nelle ricerche su Google.

Fai cosa (non sono sicuro se è Deminic Rodger, o ha22109) ha risposto in ModelAdmin per changelist_view

class MyModelAdmin(admin.ModelAdmin):   
    list_filter = (CustomFilter,)

    def changelist_view(self, request, extra_context=None):

        if not request.GET.has_key('decommissioned__exact'):

            q = request.GET.copy()
            q['decommissioned__exact'] = 'N'
            request.GET = q
            request.META['QUERY_STRING'] = request.GET.urlencode()
        return super(MyModelAdmin,self).changelist_view(request, extra_context=extra_context)

Quindi dobbiamo creare un SimpleListFilter personalizzato

class CustomFilter(admin.SimpleListFilter):
    title = 'Decommissioned'
    parameter_name = 'decommissioned'  # i chose to change it

def lookups(self, request, model_admin):
    return (
        ('All', 'all'),
        ('1', 'Decommissioned'),
        ('0', 'Active (or whatever)'),
    )

# had to override so that we could remove the default 'All' option
# that won't work with our default filter in the ModelAdmin class
def choices(self, cl):
    yield {
        'selected': self.value() is None,
        'query_string': cl.get_query_string({}, [self.parameter_name]),
        # 'display': _('All'),
    }
    for lookup, title in self.lookup_choices:
        yield {
            'selected': self.value() == lookup,
            'query_string': cl.get_query_string({
                self.parameter_name: lookup,
            }, []),
            'display': title,
        }

def queryset(self, request, queryset):
    if self.value() == '1':
        return queryset.filter(decommissioned=1)
    elif self.value() == '0':
        return queryset.filter(decommissioned=0)
    return queryset

Ho scoperto che avevo bisogno di usare la funzione "force_text" (aka force_unicode) nella chiamata yield nella funzione scelte, altrimenti l'opzione di filtro selezionata non sarebbe stata visualizzata come "selezionata". Ovvero "'selected': self.value () == force_text (lookup)"
MagicLAMP

1

Ecco la versione più pulita che sono stato in grado di generare di un filtro con un "Tutto" ridefinito e un valore predefinito selezionato.

Se mi mostra per impostazione predefinita i viaggi attualmente in corso.

class HappeningTripFilter(admin.SimpleListFilter):
    """
    Filter the Trips Happening in the Past, Future or now.
    """
    default_value = 'now'
    title = 'Happening'
    parameter_name = 'happening'

    def lookups(self, request, model_admin):
        """
        List the Choices available for this filter.
        """
        return (
            ('all', 'All'),
            ('future', 'Not yet started'),
            ('now', 'Happening now'),
            ('past', 'Already finished'),
        )

    def choices(self, changelist):
        """
        Overwrite this method to prevent the default "All".
        """
        value = self.value() or self.default_value
        for lookup, title in self.lookup_choices:
            yield {
                'selected': value == force_text(lookup),
                'query_string': changelist.get_query_string({
                    self.parameter_name: lookup,
                }, []),
                'display': title,
            }

    def queryset(self, request, queryset):
        """
        Returns the Queryset depending on the Choice.
        """
        value = self.value() or self.default_value
        now = timezone.now()
        if value == 'future':
            return queryset.filter(start_date_time__gt=now)
        if value == 'now':
            return queryset.filter(start_date_time__lte=now, end_date_time__gte=now)
        if value == 'past':
            return queryset.filter(end_date_time__lt=now)
        return queryset.all()

0

Creata una sottoclasse Filtro riutilizzabile, ispirata da alcune delle risposte qui (principalmente di Greg).

Vantaggi:

Riutilizzabile - Collegabile a qualsiasi ModelAdminclasse standard

Estendibile - Facile aggiungere logica aggiuntiva / personalizzata per il QuerySetfiltraggio

Facile da usare : nella sua forma più semplice, è necessario implementare solo un attributo personalizzato e un metodo personalizzato (a parte quelli richiesti per la sottoclasse SimpleListFilter)

Amministratore intuitivo : il collegamento del filtro "Tutto" funziona come previsto; come tutti gli altri

Nessun reindirizzamento : non è necessario ispezionare il GETpayload della richiesta, indipendente da HTTP_REFERER(o qualsiasi altra roba relativa alla richiesta, nella sua forma base)

Nessuna manipolazione della vista (elenco modifiche) - E nessuna manipolazione del modello (dio non voglia)

Codice:

(la maggior parte dei messaggi importsono solo per suggerimenti ed eccezioni sul tipo)

from typing import List, Tuple, Any

from django.contrib.admin.filters import SimpleListFilter
from django.contrib.admin.options import IncorrectLookupParameters
from django.contrib.admin.views.main import ChangeList
from django.db.models.query import QuerySet
from django.utils.encoding import force_str
from django.utils.translation import gettext_lazy as _
from django.core.exceptions import ValidationError


class PreFilteredListFilter(SimpleListFilter):

    # Either set this or override .get_default_value()
    default_value = None

    no_filter_value = 'all'
    no_filter_name = _("All")

    # Human-readable title which will be displayed in the
    # right admin sidebar just above the filter options.
    title = None

    # Parameter for the filter that will be used in the URL query.
    parameter_name = None

    def get_default_value(self):
        if self.default_value is not None:
            return self.default_value
        raise NotImplementedError(
            'Either the .default_value attribute needs to be set or '
            'the .get_default_value() method must be overridden to '
            'return a URL query argument for parameter_name.'
        )

    def get_lookups(self) -> List[Tuple[Any, str]]:
        """
        Returns a list of tuples. The first element in each
        tuple is the coded value for the option that will
        appear in the URL query. The second element is the
        human-readable name for the option that will appear
        in the right sidebar.
        """
        raise NotImplementedError(
            'The .get_lookups() method must be overridden to '
            'return a list of tuples (value, verbose value).'
        )

    # Overriding parent class:
    def lookups(self, request, model_admin) -> List[Tuple[Any, str]]:
        return [(self.no_filter_value, self.no_filter_name)] + self.get_lookups()

    # Overriding parent class:
    def queryset(self, request, queryset: QuerySet) -> QuerySet:
        """
        Returns the filtered queryset based on the value
        provided in the query string and retrievable via
        `self.value()`.
        """
        if self.value() is None:
            return self.get_default_queryset(queryset)
        if self.value() == self.no_filter_value:
            return queryset.all()
        return self.get_filtered_queryset(queryset)

    def get_default_queryset(self, queryset: QuerySet) -> QuerySet:
        return queryset.filter(**{self.parameter_name: self.get_default_value()})

    def get_filtered_queryset(self, queryset: QuerySet) -> QuerySet:
        try:
            return queryset.filter(**self.used_parameters)
        except (ValueError, ValidationError) as e:
            # Fields may raise a ValueError or ValidationError when converting
            # the parameters to the correct type.
            raise IncorrectLookupParameters(e)

    # Overriding parent class:
    def choices(self, changelist: ChangeList):
        """
        Overridden to prevent the default "All".
        """
        value = self.value() or force_str(self.get_default_value())
        for lookup, title in self.lookup_choices:
            yield {
                'selected': value == force_str(lookup),
                'query_string': changelist.get_query_string({self.parameter_name: lookup}),
                'display': title,
            }

Esempio di utilizzo completo:

from django.contrib import admin
from .models import SomeModelWithStatus


class StatusFilter(PreFilteredListFilter):
    default_value = SomeModelWithStatus.Status.FOO
    title = _('Status')
    parameter_name = 'status'

    def get_lookups(self):
        return SomeModelWithStatus.Status.choices


@admin.register(SomeModelWithStatus)
class SomeModelAdmin(admin.ModelAdmin):
    list_filter = (StatusFilter, )

Spero che questo aiuti qualcuno; feedback sempre apprezzato.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.