Django ManyToMany通过集合大小或成员进行过滤 [英] Django ManyToMany filtering by set size or member in the set

查看:181
本文介绍了Django ManyToMany通过集合大小或成员进行过滤的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用 django 来维护消息的数据库。

其中我有以下模型

I am using django to maintain a database of messages.
Among others I have the following models:

class User(models.Model):
    id = models.IntegerField(primary_key=True)
    name = models.CharField(max_length=10)

class Message(models.Model):
    id = models.IntegerField(primary_key=True)
    body = models.CharField(max_length=200)
    users = models.ManyToManyField(User)

我正在尝试写一个对于给定的用户给出了他(和他一个人)相关联的消息的实用方法。

I am trying to write a utility method that for a given user gives me the messages he (and he alone) is associated with.

ie for:

m1 = Message(id=1, body='Some body')
m1.save()
m2 = Message(id=2, body='Another body')
m2.save()
m3 = Message(id=3, body='And yet another body')
m3.save()

u1 = User(name='Jesse James')
u1.save()
u2 = User(name='John Doe')
u2.save()

m1.users.add(u1, u2)
m2.users.add(u1)
m3.users.add(u2)

getMessagesFor('Jesse James')

只返回 m2

假设我有用户正确的模型实例,它归结为一行,我已经尝试了这些:

Will return only m2.
Assuming I have in user the right model instance, it boils down to one line, and I have tried these following:

    user.message_set.annotate(usr_cnt=Count('users')).filter(usr_cnt__lte=1)

或:

    messages = Message.objects.filter(users__id__in=[user.id])

和:

    messages = Message.objects.filter(users__id__exact=user.id)

And:

    messages = Message.objects.filter(users__contains=user)

等等...我总是得到 m2 AND m1

And so on... I always get both m2 AND m1.
Tried annotations, excludes, filters etc.

有人可以帮助我吗?

推荐答案

qs = Message.objects.annotate(cc=Count('users')).filter(cc=1)

以上查询将返回只有一个用户关联的所有邮件。

Above query will return all messages which has only single user associated with it.

要按用户过滤,请根据用户添加另一个筛选器:根据用户过滤注释查询:

To filter by user, add another filter at end to filter the annotated query according to user:

qs = Message.objects.annotate(cc=Count('users')).filter(cc=1).filter(users__id=user.id)
# if user user.id=1, this will return only m2

这篇关于Django ManyToMany通过集合大小或成员进行过滤的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆