##// END OF EJS Templates
New backend for fav threads. Now only last post ids are saved, no thread ids
neko259 -
r2044:227641ed default
parent child Browse files
Show More
@@ -1,9 +1,7 b''
1 from boards import settings
1 import boards
2 2 from boards.models import Tag, TagAlias, Attachment
3 3 from boards.models.attachment import AttachmentSticker
4 from boards.models.thread import FAV_THREAD_NO_UPDATES
5 4 from boards.models.user import UserSettings
6 from boards.settings import SECTION_VIEW
7 5
8 6 MAX_TRIPCODE_COLLISIONS = 50
9 7
@@ -20,6 +18,7 b" SETTING_LAST_NOTIFICATION_ID = 'last_not"
20 18 SETTING_IMAGE_VIEWER = 'image_viewer'
21 19 SETTING_IMAGES = 'images_aliases'
22 20 SETTING_ONLY_FAVORITES = 'only_favorites'
21 SETTING_LAST_POSTS = 'last_posts'
23 22
24 23 DEFAULT_THEME = 'md'
25 24
@@ -102,31 +101,32 b' class SettingsManager:'
102 101 tags.remove(tag.get_name())
103 102 self.set_setting(SETTING_HIDDEN_TAGS, tags)
104 103
105 def get_fav_threads(self) -> dict:
106 return self.get_setting(SETTING_FAVORITE_THREADS, default=dict())
107
108 104 def add_or_read_fav_thread(self, opening_post):
109 threads = self.get_fav_threads()
105 last_post_ids = self.get_setting(SETTING_LAST_POSTS)
106 if not last_post_ids:
107 last_post_ids = []
110 108
111 max_fav_threads = settings.get_int(SECTION_VIEW, 'MaxFavoriteThreads')
112 if (str(opening_post.id) in threads) or (len(threads) < max_fav_threads):
113 thread = opening_post.get_thread()
114 # Don't check for new posts if the thread is archived already
115 if thread.is_archived():
116 last_id = FAV_THREAD_NO_UPDATES
117 else:
118 last_id = thread.get_replies().last().id
119 threads[str(opening_post.id)] = last_id
120 self.set_setting(SETTING_FAVORITE_THREADS, threads)
109 self.del_fav_thread(opening_post)
110
111 last_post_id = opening_post.get_thread().get_replies().last().id
112 last_post_ids.append(last_post_id)
113
114 self.set_setting(SETTING_LAST_POSTS, last_post_ids)
121 115
122 116 def del_fav_thread(self, opening_post):
123 threads = self.get_fav_threads()
124 if self.thread_is_fav(opening_post):
125 del threads[str(opening_post.id)]
126 self.set_setting(SETTING_FAVORITE_THREADS, threads)
117 last_posts_ids = self.get_setting(SETTING_LAST_POSTS)
118
119 for post in self.get_last_posts():
120 if post.get_thread() == opening_post.get_thread():
121 last_posts_ids.remove(post.id)
122
123 self.set_setting(SETTING_LAST_POSTS, last_posts_ids)
127 124
128 125 def thread_is_fav(self, opening_post):
129 return str(opening_post.id) in self.get_fav_threads()
126 for post in self.get_last_posts():
127 if post.get_thread() == opening_post.get_thread():
128 return True
129 return False
130 130
131 131 def get_notification_usernames(self):
132 132 names = set()
@@ -178,6 +178,10 b' class SettingsManager:'
178 178 hidden_tag_names = self.get_setting(SETTING_HIDDEN_TAGS)
179 179 return hidden_tag_names is not None and tag.get_name() in hidden_tag_names
180 180
181 def get_last_posts(self):
182 post_ids = self.get_setting(SETTING_LAST_POSTS) or []
183 return [boards.models.Post.objects.get(id=post_id) for post_id in post_ids]
184
181 185
182 186 class SessionSettingsManager(SettingsManager):
183 187 """
@@ -202,6 +206,8 b' class SessionSettingsManager(SettingsMan'
202 206 class DatabaseSettingsManager(SessionSettingsManager):
203 207 def __init__(self, session):
204 208 super().__init__(session)
209 if not session.session_key:
210 session.save()
205 211 self.settings, created = UserSettings.objects.get_or_create(session_key=session.session_key)
206 212
207 213 def add_fav_tag(self, tag):
@@ -39,14 +39,10 b' def get_notifications(context, settings_'
39 39
40 40
41 41 def get_new_post_count(context, settings_manager):
42 fav_threads = settings_manager.get_fav_threads()
43 if fav_threads:
44 fav_thread_ops = Post.objects.filter(id__in=fav_threads.keys()) \
45 .order_by('-pub_time').only('thread_id', 'pub_time')
46 ops = [{'op': op, 'last_id': fav_threads[str(op.id)]} for op in fav_thread_ops]
47 count = Thread.objects.get_new_post_count(ops)
48 if count > 0:
49 context[CONTEXT_NEW_POST_COUNT] = '(+{})'.format(count)
42 last_posts = settings_manager.get_last_posts()
43 count = Thread.objects.get_new_post_count(last_posts)
44 if count > 0:
45 context[CONTEXT_NEW_POST_COUNT] = '(+{})'.format(count)
50 46
51 47
52 48 def user_and_ui_processor(request):
@@ -75,7 +71,7 b' def user_and_ui_processor(request):'
75 71 default=settings.get(SECTION_VIEW, 'DefaultImageViewer'))
76 72
77 73 context[CONTEXT_HAS_FAV_THREADS] =\
78 len(settings_manager.get_fav_threads()) > 0
74 len(settings_manager.get_last_posts()) > 0
79 75
80 76 context[CONTEXT_BANNERS] = Banner.objects.order_by('-id')
81 77 context[CONTEXT_ONLY_FAVORITES] = settings_manager.get_setting(
@@ -60,13 +60,11 b' class ThreadManager(models.Manager):'
60 60 thread.update_posts_time()
61 61 thread.save(update_fields=['last_edit_time', 'status'])
62 62
63 def get_new_posts(self, datas):
63 def get_new_posts(self, last_posts):
64 64 query = None
65 # TODO Use classes instead of dicts
66 for data in datas:
67 if data['last_id'] != FAV_THREAD_NO_UPDATES:
68 q = (Q(id=data['op'].get_thread_id())
69 & Q(replies__id__gt=data['last_id']))
65 for post in last_posts:
66 if not post.get_thread().is_archived():
67 q = Q(id=post.thread_id) & Q(replies__id__gt=post.id)
70 68 if query is None:
71 69 query = q
72 70 else:
@@ -75,8 +73,8 b' class ThreadManager(models.Manager):'
75 73 return self.filter(query).annotate(
76 74 new_post_count=Count('replies'))
77 75
78 def get_new_post_count(self, datas):
79 new_posts = self.get_new_posts(datas)
76 def get_new_post_count(self, last_posts):
77 new_posts = self.get_new_posts(last_posts)
80 78 return new_posts.aggregate(total_count=Count('replies'))\
81 79 ['total_count'] if new_posts else 0
82 80
@@ -290,27 +290,25 b' def api_get_new_posts(request):'
290 290 include_posts = 'include_posts' in request.GET
291 291
292 292 settings_manager = get_settings_manager(request)
293 fav_threads = settings_manager.get_fav_threads()
294 fav_thread_ops = Post.objects.filter(id__in=fav_threads.keys())\
295 .order_by('-pub_time').prefetch_related('thread')
296 293
297 ops = [{'op': op, 'last_id': fav_threads[str(op.id)]} for op in fav_thread_ops]
294 last_posts = settings_manager.get_last_posts()
298 295 if include_posts:
299 new_post_threads = Thread.objects.get_new_posts(ops)
296 new_post_threads = Thread.objects.get_new_posts(last_posts)
300 297 if new_post_threads:
301 298 thread_ids = {thread.id: thread for thread in new_post_threads}
302 299 else:
303 300 thread_ids = dict()
304 301
305 for op in fav_thread_ops:
302 for post in last_posts:
306 303 fav_thread_dict = dict()
307 304
308 op_thread = op.get_thread()
309 if op_thread.id in thread_ids:
310 thread = thread_ids[op_thread.id]
305 thread = post.get_thread()
306 op = thread.get_opening_post()
307 if thread.id in thread_ids:
308 thread = thread_ids[thread.id]
311 309 new_post_count = thread.new_post_count
312 310 fav_thread_dict['newest_post_link'] = thread.get_replies()\
313 .filter(id__gt=fav_threads[str(op.id)])\
311 .filter(id__gt=post.id)\
314 312 .first().get_absolute_url(thread=thread)
315 313 else:
316 314 new_post_count = 0
@@ -325,7 +323,7 b' def api_get_new_posts(request):'
325 323 else:
326 324 fav_thread_dict = dict()
327 325 fav_thread_dict['new_post_count'] = \
328 Thread.objects.get_new_post_count(ops)
326 Thread.objects.get_new_post_count(last_posts)
329 327 posts.append(fav_thread_dict)
330 328
331 329 return HttpResponse(content=json.dumps(posts))
@@ -53,9 +53,9 b' class FavoritesFilter(FeedFilter):'
53 53 favorites = 'favorites' in request.GET
54 54 if favorites:
55 55 settings_manager = get_settings_manager(request)
56 fav_thread_ops = Post.objects.filter(id__in=settings_manager.get_fav_threads().keys())
57 fav_threads = [op.get_thread() for op in fav_thread_ops]
58 filtered_posts = filtered_posts.filter(thread__in=fav_threads)
56 last_posts = settings_manager.get_last_posts()
57 threads = [post.get_thread() for post in last_posts]
58 filtered_posts = filtered_posts.filter(thread__in=threads)
59 59 return filtered_posts
60 60
61 61
General Comments 0
You need to be logged in to leave comments. Login now