在学习Django-Paginator的时候,遇到了一个现象,当get_page(number=0)的时候,只取到了4条记录(我设置了每页取5条数据)
贴上代码,还原现象的经过如下:
整个逻辑:前端获取到当前的新闻分类id(tag)和当前页码(page),将这两个值传给后端,后端通过Django的ORM对数据进行过滤,取出符合逻辑的数据,把所有的数据放进list中返回给前端,前端使用js拼接的方式显示最终数据。
- 数据库中的记录
- 前端代码
- views.py中的代码
- 为这个类视图配置路由
- 用url的方式去访问该路由
得到的返回结果:
问题来了:
我设置了每页取5条数据,为什么通过直接的路由访问只能得到4条数据? - 尝试一下用正常访问的方式
完全正常,控制台打印出了5条数据。
具体原因
原因是get_page()的容错机制遇到了number=0的时候,会去调用num_pages()这个方法,从而设置一个number值。但这个number值是总数据量除以每页数量的结果。
- 首先要得到一些参数
在views.py中添加一些print()函数,打印部分参数的值,方便自己查找问题所在。
所需参数:当前第几页、一共有多少记录、每页5个数据一共有几页,数据如下控制台打印所示
代码修改如下:
再次去访问url,然后回到pycharm的控制台中查看输出了些什么:
此时的page是等于0,而正常访问首页面的时候,获得的page=1
那么我怀疑,可能是因为page=0的时候出了问题
- 接着去看get_page(number)这个方法到底做了那些事情
根据上图所现,可以得知page=0,那么在调用get_page(number)这个方法的时候,number就是等于0了
点到num_pages()这个方法中去:
得到的结果:
可以看到,无论是url直接访问路由,还是正常前端访问。得到的num_pages()都是178
通过Python Shell可以看一下ceil()这个方法的返回值:
num_pages()这个方法使命结束,返回结果,代码重新回去到get_pages()方法中:
其实,整个page(number)方法实现分页的逻辑,就靠这个self.object_list[bottom:top],分片取值:
通过下面这个分片实验可以得知,[885:889]只能获取到4条数据:
个人对自己的建议
问题解决,是因为page=0的缘故造成num_pages()给了"默认值"。
那么解决方案很简单,把page=int(request.GET.get("page", 1))这条语句中的0,改成1即可(没有获取到"page"的值,就默认给1):
结果完全符合预期,问题解决
控制台中的打印信息:
浏览器中也正常获取到了5条数据: