Django Paginator
Django 分页官方文档 https://docs.djangoproject.com/en/1.10/topics/pagination/
此分页方法没有限制显示出来的页码的个数,会显示全部的页码,待改进。
后端代码
由于代码是先object_list = model_obj.model.objects.all(),然后调用 paginator = Paginator(object_list, 2),如果数据量很大就会消耗很多的性能。
如果是这样呢写呢? paginator = Paginator(model_obj.model.objects.all(), 2) 这样能利用queryset的惰性机制吗?
看了下Paginator源码,应该是可行的
1 class Paginator(object): 2 3 def __init__(self, object_list, per_page, orphans=0, 4 allow_empty_first_page=True): 5 self.object_list = object_list 6 self.per_page = int(per_page) 7 self.orphans = int(orphans) 8 self.allow_empty_first_page = allow_empty_first_page 9 10 def validate_number(self, number): 11 """ 12 Validates the given 1-based page number. 13 """ 14 try: 15 number = int(number) 16 except (TypeError, ValueError): 17 raise PageNotAnInteger('That page number is not an integer') 18 if number < 1: 19 raise EmptyPage('That page number is less than 1') 20 if number > self.num_pages: 21 if number == 1 and self.allow_empty_first_page: 22 pass 23 else: 24 raise EmptyPage('That page contains no results') 25 return number 26 27 def page(self, number): 28 """ 29 Returns a Page object for the given 1-based page number. 30 """ 31 number = self.validate_number(number) 32 bottom = (number - 1) * self.per_page 33 top = bottom + self.per_page 34 if top + self.orphans >= self.count: 35 top = self.count 36 return self._get_page(self.object_list[bottom:top], number, self) 37 38 def _get_page(self, *args, **kwargs): 39 """ 40 Returns an instance of a single page. 41 42 This hook can be used by subclasses to use an alternative to the 43 standard :cls:`Page` object. 44 """ 45 return Page(*args, **kwargs) 46 47 @cached_property 48 def count(self): 49 """ 50 Returns the total number of objects, across all pages. 51 """ 52 try: 53 return self.object_list.count() 54 except (AttributeError, TypeError): 55 # AttributeError if object_list has no count() method. 56 # TypeError if object_list.count() requires arguments 57 # (i.e. is of type list). 58 return len(self.object_list) 59 60 @cached_property 61 def num_pages(self): 62 """ 63 Returns the total number of pages. 64 """ 65 if self.count == 0 and not self.allow_empty_first_page: 66 return 0 67 hits = max(1, self.count - self.orphans) 68 return int(ceil(hits / float(self.per_page))) 69 70 @property 71 def page_range(self): 72 """ 73 Returns a 1-based range of pages for iterating through within 74 a template for loop. 75 """ 76 return six.moves.range(1, self.num_pages + 1) 77 78 79 QuerySetPaginator = Paginator # For backwards-compatibility.
#需要导入 的模块 from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger def display_table_objs(request,app_name,table_name): print(app_name,'----',table_name) #获取数据库数据 model_obj = king_admin.enabled_admins[app_name][table_name] #分页 object_list = model_obj.model.objects.all() paginator = Paginator(object_list, 2) # Show 2 contacts per page # paginator = JuncheePaginator(object_list, 1) # Show 2 contacts per page page = request.GET.get('page') try: contacts = paginator.page(page) except PageNotAnInteger: # If page is not an integer, deliver first page. contacts = paginator.page(1) except EmptyPage: # If page is out of range (e.g. 9999), deliver last page of results. contacts = paginator.page(paginator.num_pages) return render(request,'king_admin/table_objs.html',{"model_obj":model_obj, "query_sets":contacts,})
前端模板代码
其中的标签样式引用的Bootstrap的样式
<ul class="pagination"> {# topics.paginator.page_range 这个函数返回包含一个所有页码数的 range 对象 #} {# 即 range(1, topics.paginator.num_pages + 1) #} {% if query_sets.has_previous %} <li><a href="?page={{ query_sets.previous_page_number }}">上一页</a></li> {% else %} <li><span>没了</span></li> {% endif %} {% for page_number in query_sets.paginator.page_range %} {% ifequal page_number query_sets.number %} <li class="disabled"><span>{{ page_number }}</span></li> {% else %} <li ><a href="?page={{ page_number }}">{{ page_number }}</a></li> {% endifequal %} {% endfor %} {% if query_sets.has_next %} <li><a href="?page={{ query_sets.next_page_number }}">下一页</a></li> {% else %} <li><span>没了</span></li> {% endif %} </ul>
效果如下: