Django 注释模型并过滤特定值

Django annotate model and filter for specific value

我正在尝试使用 djangos annotate,但不太清楚它是如何工作的。

我有一个函数,我想在其中注释客户的查询集,过滤他们和 return 客户数量

def my_func(self):
    received_signatures = self.customer_set.annotate(Count('registrations').filter().count()

现在对于过滤器部分,这就是我在弄清楚如何做到这一点时遇到的问题。我要过滤的是我的 received_signatures,这是在我的 customer.py

中调用的函数
def received_signatures(self):
    signatures = [reg.brought_signature for reg in self.registrations.all() if reg.status == '1_YES']
    if len(signatures): 
        return all(signatures)
    else:
       return None

brough_signature 是一个数据库字段

那么我如何注释查询集,过滤 received_signatures 然后 return 一个数字?

相关型号信息:

class Customer(models.Model):
    brought_signature = models.BooleanField(u'Brought Signature', default=False)


class Registration(models.Model):
    brought_signature = models.BooleanField(u'Brought Signature', default=False)
    status = models.CharField(u'Status', max_length=10, choices=STATUS_CHOICES, default='4_RECEIVED')

注:一个参与者和一个注册可以有brought_signature。我的程序中有一个设置允许我 A) 仅在我的参与者处标记 brought_signature(这意味着他为他的所有注册带来了签名)或 B)在他的每个注册中标记 brought_signature

对于这种情况,选项 B) 是相关的。通过我的received_signatures,我检查客户是否为他的状态为“1_YES”的每个注册带来了每个签名,我想计算所有这样做的客户和return一个数字(然后我将其用于 pygal 图表的另一个函数)

如果我理解正确,你想检查 all Registrations 对于给定的 Customerstatus == '1_YES 是否应该有作为属性.brought_signature = True,至少应该有这样的值。有几种方法可以做到这一点。

我们可以这样写:

received_signatures = self.customer_set.filter(
    registration__status='1_YES'
).annotate(
    minb=Min('registration__brought_signature')
).filter(
    minb__gt=0
).count()

所以我们在这里做的是首先 .filter(..) 在状态为 1_YESregistration 上,接下来我们为每个客户计算一个值 minb 即这些 Registrationbrought_signature 最小值。因此,如果相关 Registrationbrought_signature 之一是 False(在通常为 0 的数据库中),则 Min(..)False 还有。如果所有 brought_signature 都是 True(在通常是 1 的数据库中),那么结果是 1,然后我们可以过滤 [=18] =] 因此应该大于 0.

所以 Customers with no Registration will not, Customers没有 Registration 且状态为 1_YES,将不被计算在内,CustomerRegistration 有一个 Registration 且状态为 1_YES , 但 brough_signature 将不被计算在内。只有 Customerall Registration 具有状态 1_YES(本身不是 all Registrations) 有 brough_signature = True 被计算在内。