我在Django中具有如下页面视图,设置如下:
blog = get_object_or_404(Blog, subdomain=extracted.subdomain)
all_posts = Post.objects.filter(
blog=blog, publish=True).order_by('-published_date')
nav = all_posts.filter(is_page=True)
posts = all_posts.filter(is_page=False)
这将导致DB被访问3次。我试图对此进行优化,使其仅访问数据库一次。以下代码段将调用次数减少到2,但是我敢肯定还有比我不知道的更好的方法。
blog = get_object_or_404(Blog, subdomain=extracted.subdomain)
all_posts = Post.objects.filter(
blog=blog, publish=True).order_by('-published_date')
nav = []
posts = []
for post in all_posts:
if post.is_page:
nav.append(post)
else:
posts.append(post)
据我了解,prefetch_related
和select_related
是相反的,我不确定如何在这种情况下实现它们。
我的模型设置如下:
class Blog(models.Model):
user = models.ForeignKey(User, on_delete=models.CASCADE, blank=True)
title = models.CharField(max_length=200)
...
class Post(models.Model):
blog = models.ForeignKey(
Blog,
on_delete=models.CASCADE,
related_name='post')
title = models.CharField(max_length=200)
...
提前感谢!
编辑:
由于某种原因,它将执行3个DB请求
blog = get_object_or_404(Blog.objects.prefetch_related('post_set'), subdomain=extracted.subdomain)
posts = blog.post_set.filter(publish=True).order_by('-published_date')
某些事物:
也就是说,要摆脱多余的查询:
posts = Post.objects.filter(
blog__subdomain=extracted_subdomain, publish=True
).order_by('-published_date')
if not posts:
raise Http404('no posts for subdomain')
并且确保您可以从帖子访问博客属性,而无需每次迭代查询:
posts = Post.objects.filter(
blog__subdomain=extracted_subdomain, publish=True
).select_related('blog').order_by('-published_date')