Как создать фильтр по умолчанию в наборе запросов django

У меня есть следующая модель в моем приложении django.

class Segment(BaseSegmentModel):
    payload_json = JSONField(null=True, default=None, blank=True)
    owner = models.ForeignKey(CustomUser, null=True, blank=True, on_delete=models.SET_NULL, related_name='segments')
    name = models.CharField(max_length=100, null=True, blank=False)
    status = models.CharField(max_length=100, null=True, blank=True, choices=SegmentStatuses.choices, default=SegmentStatuses.STOPPED)
    created_date = models.DateTimeField(null=True, auto_now_add=True)as

Существует поле status, которое имеет три значения,

Active
Running
Archive

Мне нужно добавить фильтр по умолчанию на эту модель, где она не должна показывать результаты со статусом = Архив.

Поэтому всякий раз, когда кто-то запрашивает эту модель, она не должна показывать никаких архивных результатов.

В представлении вы можете сделать это с помощью exclude():

views.py:

Segment.objects.exclude(status='archive')

Редактирование:

Вы можете переопределить get_queryset менеджера.

Пример:

models.py

class AnyManager(models.Manager):
    def get_queryset(self):
        qs = super().get_queryset()
        return qs.exclude(status='archive')

class Segment(BaseSegmentModel):
    payload_json = JSONField(null=True, default=None, blank=True)
    owner = models.ForeignKey(CustomUser, null=True, blank=True, on_delete=models.SET_NULL, related_name='segments')
    name = models.CharField(max_length=100, null=True, blank=False)
    status = models.CharField(max_length=100, null=True, blank=True, choices=SegmentStatuses.choices, default=SegmentStatuses.STOPPED)
    created_date = models.DateTimeField(null=True, auto_now_add=True)

    objects = AnyManager()

Это исключит поля, которые имеют status='archive', так что теперь вы можете сделать это напрямую как:

views.py:

Segment.objects.all()

Вы можете иметь 2 менеджера для вашей модели: один для всех объектов и один для исключенных объектов

class SegmentStatuses:
    STOPPED = 'stopped'
    ACTIVE = 'active'
    ARCHIVE = 'archive'

    choices = ((STOPPED, STOPPED), (ACTIVE, ACTIVE), (ARCHIVE, ARCHIVE))

class UnArchivedManager(models.Manager):
    def get_queryset(self):
        return super(UnArchivedManager, self).get_queryset().exclude(status=SegmentStatuses.ARCHIVE)


class Segment(BaseSegmentModel):
    payload_json = JSONField(null=True, default=None, blank=True)
    owner = models.ForeignKey(CustomUser, null=True, blank=True, on_delete=models.SET_NULL, related_name='segments')
    name = models.CharField(max_length=100, null=True, blank=False)
    status = models.CharField(max_length=100, null=True, blank=True, choices=SegmentStatuses.choices, default=SegmentStatuses.STOPPED)
    created_date = models.DateTimeField(null=True, auto_now_add=True)
    
    objects = UnArchivedManager()
    objects_all = models.Manager()

Как вы можете видеть на этом изображении, у меня только один объект в DB и он имеет статус 'archive', поэтому когда я использовал менеджер 'object', я не увидел ни одного объекта в результате, но когда я использовал менеджер 'object_all', я увидел 1 объект в результате

примерные запросы

Если вы вообще не хотите иметь доступ к архивному состоянию, вы можете игнорировать менеджер objects_all.

Вернуться на верх