如何过滤 ManyToMany 对象的父属性?
How do I filter parents properties of ManyToMany Object?
我是 Django 的新手,今天遇到了问题
我有两个模型,Program
和 Member
。
models.py
from django.db import models
from django.db.models import Sum
class Program(models.Model):
name = models.CharField(max_length=200)
fee = models.IntegerField(default=10) # Arbitrary Property
class Member(models.Model):
programs = models.ManyToManyField(Program, related_name='members')
name = models.CharField(max_length=200)
# I tried this but it gives me all of the sum of all the programs' fees :
# fees_for_member = models.IntegerField(default=Program.objects.prefetch_related('members').aggregate(Sum('fee'))['fee__sum'])
# This results in an error:
# fees_for_member = programs.aggregate(Sum('fee'))['fee__sum']
每个程序都有一个 fee
,Member
有一个名为 fees_for_member
或 fees
的 IntegerField,其默认值是所有 Program fees
Member
已注册。
我的问题是,如何过滤 仅 member
所在的 Programs
?
我试过 Program.objects.prefetch_related('members').aggregate(Sum('fee'))['fee__sum'])
但它 returns 是 所有 项目费用的总和。
我也试过 programs.aggregate(Sum('fee'))['fee_sum']
但是它给了我这个错误:
AttributeError: 'ManyToManyField' object has no attribute 'aggregate'
我能为此做什么?我知道我错过了一些东西,但我不确定它是什么。我花了几个小时搜索 Django 文档和 SO,但我找不到答案,因此不胜感激。
您应该为 fees_for_member 定义一个 属性 而不是一个字段,因为这必须动态计算:
class Member(models.Model):
programs = models.ManyToManyField(Program, related_name='members')
name = models.CharField(max_length=200)
@property
def fees_for_member(self):
return self.programs.aggregate(models.Sum('fee'))['fee__sum']
这应该有效。
方案二:
如果 Program.fee 也是 属性,并且属性是 python 代码(不是数据库中的值),则不能使用数据库级别的操作。等效的解决方案是:
class Member(models.Model):
programs = models.ManyToManyField(Program, related_name='members')
name = models.CharField(max_length=200)
@property
def fees_for_member(self):
return sum([p.fee for p in self.programs.all()])
关于这个的一些文档:
https://docs.djangoproject.com/en/3.0/topics/db/models/#model-methods
我是 Django 的新手,今天遇到了问题
我有两个模型,Program
和 Member
。
models.py
from django.db import models
from django.db.models import Sum
class Program(models.Model):
name = models.CharField(max_length=200)
fee = models.IntegerField(default=10) # Arbitrary Property
class Member(models.Model):
programs = models.ManyToManyField(Program, related_name='members')
name = models.CharField(max_length=200)
# I tried this but it gives me all of the sum of all the programs' fees :
# fees_for_member = models.IntegerField(default=Program.objects.prefetch_related('members').aggregate(Sum('fee'))['fee__sum'])
# This results in an error:
# fees_for_member = programs.aggregate(Sum('fee'))['fee__sum']
每个程序都有一个 fee
,Member
有一个名为 fees_for_member
或 fees
的 IntegerField,其默认值是所有 Program fees
Member
已注册。
我的问题是,如何过滤 仅 member
所在的 Programs
?
我试过 Program.objects.prefetch_related('members').aggregate(Sum('fee'))['fee__sum'])
但它 returns 是 所有 项目费用的总和。
我也试过 programs.aggregate(Sum('fee'))['fee_sum']
但是它给了我这个错误:
AttributeError: 'ManyToManyField' object has no attribute 'aggregate'
我能为此做什么?我知道我错过了一些东西,但我不确定它是什么。我花了几个小时搜索 Django 文档和 SO,但我找不到答案,因此不胜感激。
您应该为 fees_for_member 定义一个 属性 而不是一个字段,因为这必须动态计算:
class Member(models.Model):
programs = models.ManyToManyField(Program, related_name='members')
name = models.CharField(max_length=200)
@property
def fees_for_member(self):
return self.programs.aggregate(models.Sum('fee'))['fee__sum']
这应该有效。
方案二:
如果 Program.fee 也是 属性,并且属性是 python 代码(不是数据库中的值),则不能使用数据库级别的操作。等效的解决方案是:
class Member(models.Model):
programs = models.ManyToManyField(Program, related_name='members')
name = models.CharField(max_length=200)
@property
def fees_for_member(self):
return sum([p.fee for p in self.programs.all()])
关于这个的一些文档: https://docs.djangoproject.com/en/3.0/topics/db/models/#model-methods