Search code examples
djangopython-3.xpaginationdjango-rest-framework

How to use LimitOffSetPagination instead of PageNumberPagination in Django Rest Framework?


I have written a code in Python using Django Rest Framework to fetch data from database(MySql) and view it in browser using Pagination(LimitOffSetPagination).But It is not working fine.But when I used PageNumberPagination it was working great. so I am posting my new code.Commented parts of my code is actually for PageNumberPagination. So just ignore it. Please tell me the necessary changes needed and help me out. The error coming is:

Exception Value: index() missing 1 required positional argument: 'request'

view.py

from rest_framework.pagination import PageNumberPagination
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from rest_framework.pagination import LimitOffsetPagination


@api_view(['GET','POST'])

def index(self, request):

  if request.method=='GET':

    all_dataobj=fetchdata.objects.all()

    page = self.paginate_queryset(all_dataobj)

     if page is not None:

      pserializer = self.get_fetchdataSerializers(page, many=True)

      return self.get_paginated_response(pserializer.data)

    pserializer = self.get_fetchdataSerializers(all_dataobj, many=True)

    return Response(pserializer.data)

    # paginator = StandardResultsSetPagination()
    # result_page = paginator.paginate_queryset(all_dataobj, request)
    # pserializer=fetchdataSerializers(result_page,many=True)
    # return paginator.get_paginated_response(pserializer.data) 


 elif request.method=='POST':

  serializer=fetchdataSerializers(data=request.data)

  if serializer.is_valid():

    serializer.save()

  return Response(serializer.data,status=status.HTTP_201_CREATED)
  return Response(serializer.errors,status=status.HTTP_400_BAD_REQUEST) 

settings.py

REST_FRAMEWORK = {

      'DEFAULT_PAGINATION_CLASS': 
      'rest_framework.pagination.LimitOffsetPagination',
      'PAGE_SIZE': 10
      }

urls.py

urlpatterns = [
path('', m.index, name='index'),
]

I am even posting the pagination.py file which I was using earlier for PageNumberPagination. Please do suggest me if there is any necessary changes needed to be done or I should remove the file as a whole itself????

pagination.py

from rest_framework import pagination

class StandardResultsSetPagination(pagination.PageNumberPagination):
page_size = 10
page_query_param = 'page'
page_size_query_param = 'per_page'
max_page_size = 1000

Solution

  • Actually I solved this problem myself...so felt like posting the solution...It may come in help to someone...so I am posting the view.py, pagination.py and settings.py files...

    view.py

    from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
    from .pagination import CustomPagination
    
    
    @api_view(['GET','POST'])
    
    def index(request):
    
      if request.method=='GET':
    
        all_dataobj=fetchdata.objects.all()
    
        paginator = CustomPagination()
        result_page = paginator.paginate_queryset(all_dataobj, request)
    
        pserializer=fetchdataSerializers(result_page,many=True)
    
        return paginator.get_paginated_response(pserializer.data) 
    
    
      elif request.method=='POST':
    
        serializer=fetchdataSerializers(data=request.data)
    
        if serializer.is_valid():
    
          serializer.save()
    
        return Response(serializer.data,status=status.HTTP_201_CREATED)
        return Response(serializer.errors,status=status.HTTP_400_BAD_REQUEST) 
    

    pagination.py

        class CustomPagination(pagination.LimitOffsetPagination):
    
          default_limit = 1000
          max_limit = 1000000
          min_limit = 1
          min_offset = 0
          max_offset = 1000000
    
           def paginate_queryset(self, queryset, request, view=None):
    
             limit = request.query_params.get('limit')
             offset = request.query_params.get('offset')
    
             if limit:
    
                limit = int(limit)
    
                if limit > self.max_limit:
    
                  raise serializers.ValidationError({"limit" : ["Limit should be less 
                  than or equal to {0}".format(self.max_limit)]})
    
                elif limit < self.min_limit:
    
                  raise serializers.ValidationError({"limit" : ["Limit should be greater 
                  than or equal to {0}".format(self.min_limit)]})
    
             if offset:
    
               offset = int(offset)
    
               if offset > self.max_offset:
    
                 raise serializers.ValidationError({"offset" : ["Offset should be less 
                 than or equal to {0}".format(self.max_offset)]})
    
              elif offset < self.min_offset:
    
                raise serializers.ValidationError({"offset" : ["Offset should be greater 
                than or equal to {0}".format(self.min_offset)]})
    
             return super(self.__class__, self).paginate_queryset(queryset, request, 
             view)
    

    settings.py

    REST_FRAMEWORK = {
    # 'DEFAULT_PAGINATION_CLASS': 'rest_framework.pagination.PageNumberPagination',
    'DEFAULT_PAGINATION_CLASS': 'rest_framework.pagination.LimitOffsetPagination',
    'PAGE_SIZE': 100
     }