首页 文章

Django使用带有m2m关系的values方法/使用django过滤m2m表

提问于
浏览
0
class Book(models.Model):
    name = models.CharField(max_length=127, blank=False)

class Author(models.Model):
    name = models.CharField(max_length=127, blank=False)
    books = models.ManyToMany(Books)

我试图过滤作者所以我可以返回作者的结果集,如:

[{id: 1, name: 'Grisham', books : [{name: 'The Client'},{name: 'The Street Lawyer}], ..]

在我对作者的m2m关系之前,我能够查询任意数量的作者记录,并使用只有一个db查询的values方法获得我需要的所有值 .

但它看起来像

Author.objects.all().values('name', 'books')

会返回类似的东西:

[{id: 1, name: 'Grisham', books :{name: 'The Client'}},{id: 1, name: 'Grisham', books :{name: 'The Street Lawyer'}}]

使用values方法查看文档看起来不太可能 .
https://docs.djangoproject.com/en/dev/ref/models/querysets/

警告因为ManyToManyField属性和反向关系可以有多个相关的行,包括这些行可能会对结果集的大小产生乘数效应 . 如果在values()查询中包含多个此类字段,这将特别明显,在这种情况下,将返回所有可能的组合 .

我想尝试使用最少量的数据库命中来获得n大小的结果集 authorObject.books.all() 将导致至少n db命中 .

在django有办法做到这一点吗?

我认为使用最少量的数据库命中执行此操作的一种方法是:

authors = Authors.objects.all().values('id')
q = Q()
for id in authors:
   q = q | Q(author__id = id)

#m2m author book table.. from my understanding it is 
#not accessible in the django QuerySet
author_author_books.filter(q)  #grab all of the book ids and author ids with one query

是否有内置的方法来查询m2m author_author_books表或我是否要写sql?有没有办法利用Q()在原始sql中进行OR逻辑?

提前致谢 .

1 回答

  • 1

    我想你想要prefetch_related . 像这样的东西:

    authors = Author.objects.prefetch_related('books').all()
    

    更多关于here .

    如果要查询author_author_books表,我认为您需要指定“通过”表:

    class BookAuthor(models.Model):
      book = models.ForeignKey(Book)
      author = models.ForeignKey(Author)
    
    class Author(models.Model):
      name = models.CharField(max_length=127, blank=False)
      books = models.ManyToMany(Books, through=BookAuthor)
    

    然后你可以像任何其他模型一样查询BookAuthor .

相关问题