Search code examples
djangodjango-modelsmanytomanyfield

Django ManyToMany Through Filter


I have a model that defines categories that can be attached to an event. I'm tracking when the category was added/removed to/from the event via the through model.

class ZCategory(models.Model):
    name = models.CharField(max_length=8)

class ZCategoryInstanceThrough(models.Model):
    category = models.ForeignKey('events.ZCategory')
    event = models.ForeignKey('events.GenericModel', related_name="eventcatinstances")
    added_by = models.ForeignKey('common.User', related_name="eventcatadds")
    date_created = models.DateTimeField(auto_now_add=True)
    date_updated = models.DateTimeField(auto_now=True)
    date_removed = models.DateTimeField(null=True, blank=True) # aka 'deleted'

class GenericModel(models.Model):
    data_zs = models.ManyToManyField('ZCategory', through=ZCategoryInstanceThrough, blank=True)

When I call data_zs upon an instantiated GenericModel Queryset with .values(), By default I'd like to not have any items where date_removed isn't nulled.

Is there a straightforward way to do this?

Edit - Example Query

self.eventcatinstances.filter(**filter_args).values('data_zs').annotate(count=Count('data_zs'))

Solution

  • After further trial and error I realized how that the answer was infront of me the whole time.

    self.eventcatinstances.filter(
        zcategoryinstancethrough__date_removed__isnull=True
        zcategoryinstancethrough__isnull=False
    ).values(
        'zcategoryinstancethrough__category'
    ).annotate(
        count=Count('zcategoryinstancethrough__category')
    )