【发布时间】:2021-05-21 08:05:08
【问题描述】:
我为我的 django drf 应用程序使用了一个自定义但简单的分页类:
from rest_framework.pagination import PageNumberPagination
class CustomPagination(PageNumberPagination):
page_size = 10
page_size_query_param = "page_size"
max_page_size = 100
我还有一个 ViewSet 操作,它对继承的查询集执行一些操作并返回分页结果:
class MatchOfJobViewSet(ModelViewSet):
serializer_class = MatchSerializer
filter_backends = (DjangoFilterBackend,)
# classic filter inheriting from django_filter.FilterSet
filter_class = MatchFilter
def get_queryset(self):
job_pk = self.kwargs["job_pk"]
return Match.objects.filter(job_pk=job_pk)
@action(
detail=False,
methods=["get"],
url_path="dynamic",
serializer_class=MatchDynamicSerializer
)
def dynamic(self, request, *args, other_args, **kwargs):
"""return the list of matches with a dynamic serializer"""
# some operation on the queryset
queryset = self.get_queryset().select_related("some_field")
# apply the filters
queryset = self.filter_queryset(queryset)
# paginate
page = self.paginate_queryset(queryset)
# I use a custom serializer that takes extra arguments
# to update dynamically the fields to be serialized
serializer = self.get_serializer(page, many=True, other_args=other_args)
# unchanged from the generic list response
return self.get_paginated_response(serializer.data)
我从视图中得到的响应是这样的
{
"count": 308,
"next": "https://blabla.com?page=2&page_size=100",
"previous": "https://blabla.com?page=4&page_size=100",
"results": [...]
}
计数显示 308 个条目虽然我在数据库中签入时只有 297 个条目(这导致最后一页最终为空)
从我读到的count 参数是由分页器(这是默认的DjangoPaginator)使用相同的查询集计算的。评估后的查询集和 Paginator.count() 如何给出不同的结果?
【问题讨论】:
-
在表格中可能是
297行,这并不意味着分页类中的QuerySet.count()必须返回相同的数字。也就是说,您的 QuerySet 可能包含一些重复的行。 -
我可以看到您一直在使用
filter_backends,这可能会导致重复 -
告诉我们
MatchFilter,我相信那里会发生一些事情。就像过滤多对多关系并获得多个重复结果一样。 -
这是真的,过滤器可能会重复条目。我将检查添加 distinct(id) 是否会改变任何内容。但是它有重复的行,最后一页不会是空的,对吧?
标签: python django django-rest-framework django-pagination