Browse Source

fix #732: less hacky thread posts pagination implementation

Rafał Pitoń 8 years ago
parent
commit
7687c43e95

+ 8 - 0
misago/threads/paginator.py

@@ -9,6 +9,14 @@ class PostsPaginator(Paginator):
     Paginator that returns that makes last item on page
     Paginator that returns that makes last item on page
     repeat as first item on next page.
     repeat as first item on next page.
     """
     """
+    def __init__(self, object_list, per_page, orphans=0,
+                 allow_empty_first_page=True):
+        per_page = int(per_page) - 1
+        if orphans:
+            orphans += 1
+        super(PostsPaginator, self).__init__(
+            object_list, per_page, orphans, allow_empty_first_page)
+
     def page(self, number):
     def page(self, number):
         """
         """
         Returns a Page object for the given 1-based page number.
         Returns a Page object for the given 1-based page number.

+ 44 - 20
misago/threads/tests/test_paginator.py

@@ -10,46 +10,70 @@ class PostsPaginatorTests(TestCase):
 
 
         paginator = PostsPaginator(items, 5)
         paginator = PostsPaginator(items, 5)
         self.assertEqual(self.get_paginator_items_list(paginator), [
         self.assertEqual(self.get_paginator_items_list(paginator), [
-            [1, 2, 3, 4, 5, 6],
-            [6, 7, 8, 9, 10, 11],
-            [11, 12, 13, 14, 15, 16],
-            [16, 17, 18, 19, 20, 21],
-            [21, 22, 23, 24, 25, 26],
-            [26, 27, 28, 29, 30],
+            [1, 2, 3, 4, 5],
+            [5, 6, 7, 8, 9],
+            [9, 10, 11, 12, 13],
+            [13, 14, 15, 16, 17],
+            [17, 18, 19, 20, 21],
+            [21, 22, 23, 24, 25],
+            [25, 26, 27, 28, 29],
+            [29, 30],
         ])
         ])
 
 
     def test_paginator_orphans(self):
     def test_paginator_orphans(self):
         """paginator handles orphans"""
         """paginator handles orphans"""
-        items = [i + 1 for i in range(20)]
+        items = [i + 1 for i in range(16)]
 
 
         paginator = PostsPaginator(items, 8, 6)
         paginator = PostsPaginator(items, 8, 6)
         self.assertEqual(self.get_paginator_items_list(paginator), [
         self.assertEqual(self.get_paginator_items_list(paginator), [
-            [1, 2, 3, 4, 5, 6, 7, 8, 9],
-            [9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
+            [1, 2, 3, 4, 5, 6, 7, 8],
+            [8, 9, 10, 11, 12, 13, 14, 15, 16],
+        ])
+
+        paginator = PostsPaginator(items, 4, 4)
+        self.assertEqual(self.get_paginator_items_list(paginator), [
+            [1, 2, 3, 4],
+            [4, 5, 6, 7],
+            [7, 8, 9, 10],
+            [10, 11, 12, 13, 14, 15, 16],
+        ])
+
+        paginator = PostsPaginator(items, 5, 3)
+        self.assertEqual(self.get_paginator_items_list(paginator), [
+            [1, 2, 3, 4, 5],
+            [5, 6, 7, 8, 9],
+            [9, 10, 11, 12, 13, 14, 15, 16],
         ])
         ])
 
 
-        paginator = PostsPaginator(items, 8, 5)
-        self.assertEqual(paginator.num_pages, 2)
+        paginator = PostsPaginator(items, 6, 2)
         self.assertEqual(self.get_paginator_items_list(paginator), [
         self.assertEqual(self.get_paginator_items_list(paginator), [
-            [1, 2, 3, 4, 5, 6, 7, 8, 9],
-            [9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
+            [1, 2, 3, 4, 5, 6],
+            [6, 7, 8, 9, 10, 11],
+            [11, 12, 13, 14, 15, 16],
         ])
         ])
 
 
-        paginator = PostsPaginator(items, 9, 3)
-        self.assertEqual(paginator.num_pages, 2)
+        paginator = PostsPaginator(items, 7, 1)
         self.assertEqual(self.get_paginator_items_list(paginator), [
         self.assertEqual(self.get_paginator_items_list(paginator), [
-            [1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
-            [10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20],
+            [1, 2, 3, 4, 5, 6, 7],
+            [7, 8, 9, 10, 11, 12, 13],
+            [13, 14, 15, 16],
         ])
         ])
 
 
+        paginator = PostsPaginator(items, 7, 3)
+        self.assertEqual(self.get_paginator_items_list(paginator), [
+            [1, 2, 3, 4, 5, 6, 7],
+            [7, 8, 9, 10, 11, 12, 13, 14, 15, 16],
+        ])
+
+        paginator = PostsPaginator(items, 10, 6)
+        self.assertEqual(self.get_paginator_items_list(paginator), [items])
+
         # regression test for #732
         # regression test for #732
         items = [i + 1 for i in range(24)]
         items = [i + 1 for i in range(24)]
 
 
         paginator = PostsPaginator(items, 18, 6)
         paginator = PostsPaginator(items, 18, 6)
         self.assertEqual(paginator.num_pages, 1)
         self.assertEqual(paginator.num_pages, 1)
-        self.assertEqual(self.get_paginator_items_list(paginator), [
-            [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24],
-        ])
+        self.assertEqual(self.get_paginator_items_list(paginator), [items])
 
 
         # extra tests for catching issues in excessively long datasets
         # extra tests for catching issues in excessively long datasets
         paginator = PostsPaginator([i + 1 for i in range(144)], 14, 6)
         paginator = PostsPaginator([i + 1 for i in range(144)], 14, 6)

+ 8 - 5
misago/threads/viewmodels/posts.py

@@ -30,10 +30,6 @@ class ViewModel(object):
         posts = list(list_page.object_list)
         posts = list(list_page.object_list)
         posters = []
         posters = []
 
 
-        next_page_post = None
-        if list_page.has_next():
-            next_page_post, posts = posts[-1], next_page_post[:-1]
-
         for post in posts:
         for post in posts:
             post.category = thread.category
             post.category = thread.category
             post.thread = thread_model
             post.thread = thread_model
@@ -48,9 +44,16 @@ class ViewModel(object):
 
 
         # add events to posts
         # add events to posts
         if thread_model.has_events:
         if thread_model.has_events:
+            first_post = None
+            if list_page.has_previous():
+                first_post = posts[0]
+            last_post = None
+            if list_page.has_next():
+                last_post = posts[-1]
+
             events_limit = settings.MISAGO_EVENTS_PER_PAGE
             events_limit = settings.MISAGO_EVENTS_PER_PAGE
             posts += self.get_events_queryset(
             posts += self.get_events_queryset(
-                request, thread_model, events_limit, posts[0], next_page_post)
+                request, thread_model, events_limit, first_post, last_post)
 
 
             # sort both by pk
             # sort both by pk
             posts.sort(key=lambda p: p.pk)
             posts.sort(key=lambda p: p.pk)