Home > Net >  Global Pagination not working on DRF Project
Global Pagination not working on DRF Project

Time:12-01

I have written an API on DRF which returns a list of data based on certain conditions, but the data is very large and global pagination is not applying on it. As a result, speed slows down and therefore, data is not shown properly on a single page.

I have adding following code in settings.py file:

 REST_FRAMEWORK = {
        "DEFAULT_PAGINATION_CLASS": "rest_framework.pagination.PageNumberPagination",
        "PAGE_SIZE": 10
    }

This is my API:

class TeacherViewSet(ModelViewSet):
    queryset = Teacher.objects.all()
    serializer_class = serializers.TeacherSerializer
    authentication_classes = [TokenAuthentication]

    def list(self, request, *args, **kwargs):
        response = []
        for teacher in queryset:
            name = Student.objects.filter(teacher=teacher).values("name")
            res = {"name": name}
            response.append(res)

        return Response(response)

Any thing wrong I am doing?

CodePudding user response:

Since you are overriding list method you are disabling pagination feature. Default list method looks like this:

def list(self, request, *args, **kwargs):
    queryset = self.filter_queryset(self.get_queryset())

    page = self.paginate_queryset(queryset)
    if page is not None:
        serializer = self.get_serializer(page, many=True)
        return self.get_paginated_response(serializer.data)

    serializer = self.get_serializer(queryset, many=True)
    return Response(serializer.data)

Note paginate_queryset and get_paginated_response methods which perform pagination. So if you need to override list you should include these methods as well:

def list(self, request, *args, **kwargs):
    response = []
    queryset = self.filter_queryset(self.get_queryset())
    queryset = self.paginate_queryset(queryset)
    for teacher in queryset:
        name = Student.objects.filter(teacher=teacher).values("name")
        res = {"name": name}
        response.append(res)
    return self.get_paginated_response(response) 

Not related to original question but please note that performing DB query inside a loop is considered a bad practice and could affect performance of your view. Instead of fetching student for each teacher inside for loop consider to use prefetch_related.

  • Related