Django使用contains来过滤多对多
我试图通过多对多的关系过滤一堆对象。 因为trigger_roles字段可能包含多个条目,所以我尝试了包含filter。 但是,因为这是devise用于string我非常无奈,我应该如何过滤这个关系(你可以忽略values_list()atm。)。
此function附加到用户configuration文件:
def getVisiblePackages(self): visiblePackages = {} for product in self.products.all(): moduleDict = {} for module in product.module_set.all(): pkgList = [] involvedStatus = module.workflow_set.filter(trigger_roles__contains=self.role.id,allowed=True).values_list('current_state', flat=True)
我的工作stream模型看起来像这样(简化):
class Workflow(models.Model): module = models.ForeignKey(Module) current_state = models.ForeignKey(Status) next_state = models.ForeignKey(Status) allowed = models.BooleanField(default=False) involved_roles = models.ManyToManyField(Role, blank=True, null=True) trigger_roles = models.ManyToManyField(Role, blank=True, null=True)
虽然解决scheme可能很简单,但我的大脑不会告诉我。
谢谢你的帮助。
你有没有尝试过这样的事情:
module.workflow_set.filter(trigger_roles__in=[self.role], allowed=True)
或者如果self.role.id
不是一个pks列表:
module.workflow_set.filter(trigger_roles__id__exact=self.role.id, allowed=True)
实现这个最简单的方法是检查ManyToManyField中整个实例(而不是id)的ManyToManyField
。 这看起来实例是否在多对多的关系中。 例:
module.workflow_set.filter(trigger_roles=self.role, allowed=True)
第一个例子中的奇点几乎是正确的。 你只需要确定它是一个列表。 第二个例子,检查trigger_roles__id__exact
是一个更好的解决scheme。
module.workflow_set.filter(trigger_roles__in=[self.role.id],allowed=True)
我知道这是一个古老的问题,但是看起来OP并没有得到他所期望的答案。 如果你有两组ManyToManyFields你想比较,诀窍是使用__in
运算符,不contains
。 所以,举个例子,如果你有一个“事件”模型,在现场eventgroups
组上有一个ManyToMany来“组”,而你的用户模型(显然)是附加到组的,你可以这样查询:
Event.objects.filter(eventgroups__in=u.groups.all())