Filtering the Aggregate in the Django ORM

后端 未结 5 858
误落风尘
误落风尘 2021-02-08 14:49

I have a function that looks like this:

def post_count(self):
        return self.thread_set.aggregate(num_posts=Count(\'post\'))[\'num_posts\']
<
5条回答
  •  悲哀的现实
    2021-02-08 15:42

    Would it be ok to change around things a bit?

    As illustrated below, you could add a post_count property to the Thread class, which counts active Posts in a Thread.

    This post_count could then be used to calculate active posts in a category by adding up all active posts in all thread in a category.

    class Category(models.Model):
        name = models.CharField(max_length=100)
        slug = models.SlugField(max_length=100, blank=True, primary_key=True)
        ordering = models.IntegerField(max_length=3, default=0)
    
        @property
        def thread_count(self):
            return self.thread_set.all().count()
    
        @property
        def post_count(self): # <-- Changed
            return reduce(lambda x,y: x + y, [x.post_count for x in self.thread_set.all()])
    
    class Thread(models.Model):
        user = models.ForeignKey(User)
        category = models.ForeignKey(Category)
        title = models.CharField(max_length=100)
        slug = models.SlugField(max_length=100)
        content = models.TextField()
        created = models.DateTimeField(auto_now_add=True)
        latest_activity = models.DateTimeField(auto_now_add=True)
    
        @property
        def post_count(self): # <---- Newly added
            return self.post_set.filter(status = 'ACTIVE').count()
    
    class Post(models.Model):
        thread = models.ForeignKey(Thread)
        parent = models.ForeignKey('Post', null=True, blank=True)
        display_name = models.CharField(max_length=100)
        email = models.EmailField(db_index=True)
        ip_address = models.IPAddressField(null=True, blank=True)
        content = models.TextField()
        status = models.CharField(choices=STATUS_CHOICES, max_length=25, db_index=True, default='approved')
        created = models.DateTimeField()
    

提交回复
热议问题