Mercurial > public > sg101
comparison forums/views/main.py @ 791:0ca691cccf8d
Utilize select_related() for user & user profiles.
This commit also removes the caching of the avatar URL in the
avatar template tag. This is because we are now using select_related,
so we already have the profile & avatar when we get to the tag.
Thus we don't need to waste time querying the cache.
Removed an apparently unused member map template as well.
author | Brian Neal <bgneal@gmail.com> |
---|---|
date | Fri, 23 May 2014 21:52:41 -0500 |
parents | 9e803323a0d0 |
children | 71a671dab55d 4619290d171d |
comparison
equal
deleted
inserted
replaced
790:6a06080e7ca8 | 791:0ca691cccf8d |
---|---|
21 from django.views.decorators.http import require_POST | 21 from django.views.decorators.http import require_POST |
22 from django.db.models import F | 22 from django.db.models import F |
23 | 23 |
24 import antispam | 24 import antispam |
25 import antispam.utils | 25 import antispam.utils |
26 from bio.models import UserProfile, BadgeOwnership | 26 from bio.models import BadgeOwnership |
27 from core.paginator import DiggPaginator | 27 from core.paginator import DiggPaginator |
28 from core.functions import email_admins, quote_message | 28 from core.functions import email_admins, quote_message |
29 | 29 |
30 from forums.models import (Forum, Topic, Post, FlaggedPost, TopicLastVisit, | 30 from forums.models import (Forum, Topic, Post, FlaggedPost, TopicLastVisit, |
31 ForumLastVisit, Attachment) | 31 ForumLastVisit) |
32 from forums.forms import (NewTopicForm, NewPostForm, PostForm, MoveTopicForm, | 32 from forums.forms import (NewTopicForm, NewPostForm, PostForm, MoveTopicForm, |
33 SplitTopicForm) | 33 SplitTopicForm) |
34 from forums.unread import (get_forum_unread_status, get_topic_unread_status, | 34 from forums.unread import (get_forum_unread_status, get_topic_unread_status, |
35 get_post_unread_status, get_unread_topics) | 35 get_post_unread_status, get_unread_topics) |
36 | 36 |
168 return HttpResponseForbidden() | 168 return HttpResponseForbidden() |
169 | 169 |
170 topic.view_count = F('view_count') + 1 | 170 topic.view_count = F('view_count') + 1 |
171 topic.save(force_update=True) | 171 topic.save(force_update=True) |
172 | 172 |
173 posts = topic.posts.select_related('user') | 173 posts = topic.posts.\ |
174 select_related('user', 'user__profile').\ | |
175 prefetch_related('attachments') | |
174 | 176 |
175 paginator = create_post_paginator(posts) | 177 paginator = create_post_paginator(posts) |
176 page_num = get_page_num(request) | 178 page_num = get_page_num(request) |
177 try: | 179 try: |
178 page = paginator.page(page_num) | 180 page = paginator.page(page_num) |
179 except InvalidPage: | 181 except InvalidPage: |
180 raise Http404 | 182 raise Http404 |
181 get_post_unread_status(topic, page.object_list, request.user) | 183 get_post_unread_status(topic, page.object_list, request.user) |
182 | 184 |
183 # Attach user profiles to each post's user to avoid using | 185 # Get the BadgeOwnership & Badges for each user who has posted in the |
184 # get_user_profile() in the template. | 186 # thread. This is done to save SQL queries in the template. |
185 users = set(post.user.id for post in page.object_list) | |
186 | |
187 profiles = UserProfile.objects.filter(user__id__in=users).select_related() | |
188 profile_keys = [profile.id for profile in profiles] | |
189 user_profiles = dict((profile.user.id, profile) for profile in profiles) | |
190 | 187 |
191 last_post_on_page = None | 188 last_post_on_page = None |
189 profile_ids = [] | |
192 for post in page.object_list: | 190 for post in page.object_list: |
193 post.user.user_profile = user_profiles[post.user.id] | |
194 post.attach_list = [] | |
195 last_post_on_page = post | 191 last_post_on_page = post |
196 | 192 profile_ids.append(post.user.profile.pk) |
197 # Attach badge ownership info to the user profiles to avoid lots | 193 |
198 # of database hits in the template: | 194 bo_qs = BadgeOwnership.objects.filter(profile__in=profile_ids).\ |
199 bos_qs = BadgeOwnership.objects.filter( | 195 select_related() |
200 profile__id__in=profile_keys).select_related() | |
201 bos = collections.defaultdict(list) | 196 bos = collections.defaultdict(list) |
202 for bo in bos_qs: | 197 for bo in bo_qs: |
203 bos[bo.profile.id].append(bo) | 198 bos[bo.profile.pk].append(bo) |
204 | 199 |
205 for user_id, profile in user_profiles.iteritems(): | 200 for post in page.object_list: |
206 profile.badge_ownership = bos[profile.id] | 201 post.user.profile.badge_ownership = bos[post.user.profile.pk] |
207 | |
208 # Attach any attachments | |
209 post_ids = [post.pk for post in page.object_list] | |
210 attachments = Attachment.objects.filter(post__in=post_ids).select_related( | |
211 'embed').order_by('order') | |
212 | |
213 post_dict = dict((post.pk, post) for post in page.object_list) | |
214 for item in attachments: | |
215 post_dict[item.post.id].attach_list.append(item.embed) | |
216 | 202 |
217 last_page = page_num == paginator.num_pages | 203 last_page = page_num == paginator.num_pages |
218 | 204 |
219 if request.user.is_authenticated(): | 205 if request.user.is_authenticated(): |
220 if last_page or last_post_on_page is None: | 206 if last_page or last_post_on_page is None: |
465 form.attach_proc.save_attachments(post) | 451 form.attach_proc.save_attachments(post) |
466 | 452 |
467 return HttpResponseRedirect(post.get_absolute_url()) | 453 return HttpResponseRedirect(post.get_absolute_url()) |
468 else: | 454 else: |
469 form = PostForm(instance=post, topic_name=topic_name) | 455 form = PostForm(instance=post, topic_name=topic_name) |
470 | |
471 post.user.user_profile = post.user.profile | |
472 | 456 |
473 return render_to_response('forums/edit_post.html', { | 457 return render_to_response('forums/edit_post.html', { |
474 'forum': post.topic.forum, | 458 'forum': post.topic.forum, |
475 'topic': post.topic, | 459 'topic': post.topic, |
476 'post': post, | 460 'post': post, |