* Upgrade edx-submissions * Upgrade edx-ora2 * Upgrade edx-val * Upgrade edx-proctoring * Update all edx-platform code that depends on DRF, including: - auth_exchange - cors_csrf - embargo - enrollment - util - commerce - course_structure - discussion_api - mobile_api - notifier_api - teams - credit - profile_images - user_api - lib/api (OAuth2 and pagination)
68 lines
2.3 KiB
Python
68 lines
2.3 KiB
Python
"""
|
|
Discussion API pagination support
|
|
"""
|
|
from rest_framework.utils.urls import replace_query_param
|
|
|
|
|
|
class _Page(object):
|
|
"""
|
|
Implements just enough of the django.core.paginator.Page interface to allow
|
|
PaginationSerializer to work.
|
|
"""
|
|
def __init__(self, object_list, page_num, num_pages):
|
|
"""
|
|
Create a new page containing the given objects, with the given page
|
|
number and number of pages
|
|
"""
|
|
self.object_list = object_list
|
|
self.page_num = page_num
|
|
self.num_pages = num_pages
|
|
|
|
def has_next(self):
|
|
"""Returns True if there is a page after this one, otherwise False"""
|
|
return self.page_num < self.num_pages
|
|
|
|
def has_previous(self):
|
|
"""Returns True if there is a page before this one, otherwise False"""
|
|
return self.page_num > 1
|
|
|
|
def next_page_number(self):
|
|
"""Returns the number of the next page"""
|
|
return self.page_num + 1
|
|
|
|
def previous_page_number(self):
|
|
"""Returns the number of the previous page"""
|
|
return self.page_num - 1
|
|
|
|
|
|
def get_paginated_data(request, results, page_num, per_page):
|
|
"""
|
|
Return a dict with the following values:
|
|
|
|
next: The URL for the next page
|
|
previous: The URL for the previous page
|
|
results: The results on this page
|
|
"""
|
|
# Note: Previous versions of this function used Django Rest Framework's
|
|
# paginated serializer. With the upgrade to DRF 3.1, paginated serializers
|
|
# have been removed. We *could* use DRF's paginator classes, but there are
|
|
# some slight differences between how DRF does pagination and how we're doing
|
|
# pagination here. (For example, we respond with a next_url param even if
|
|
# there is only one result on the current page.) To maintain backwards
|
|
# compatability, we simulate the behavior that DRF used to provide.
|
|
page = _Page(results, page_num, per_page)
|
|
next_url, previous_url = None, None
|
|
base_url = request.build_absolute_uri()
|
|
|
|
if page.has_next():
|
|
next_url = replace_query_param(base_url, "page", page.next_page_number())
|
|
|
|
if page.has_previous():
|
|
previous_url = replace_query_param(base_url, "page", page.previous_page_number())
|
|
|
|
return {
|
|
"next": next_url,
|
|
"previous": previous_url,
|
|
"results": results,
|
|
}
|