插件窝 干货文章 DRF APIView中如何优雅地实现文章搜索接口的分页功能?

DRF APIView中如何优雅地实现文章搜索接口的分页功能?

Framework import PAGE search 148    来源:    2025-03-15

在 Django REST Framework (DRF) 中,使用 APIView 实现文章搜索接口的分页功能可以通过 DRF 提供的分页器(Pagination)来优雅地实现。以下是一个示例代码,展示如何在 APIView 中实现分页功能。

1. 安装和配置 DRF

首先,确保你已经安装了 Django 和 Django REST Framework。如果没有安装,可以使用以下命令进行安装:

pip install django djangorestframework

settings.py 中配置 DRF:

INSTALLED_APPS = [
    ...
    'rest_framework',
    ...
]

REST_FRAMEWORK = {
    'DEFAULT_PAGINATION_CLASS': 'rest_framework.pagination.PageNumberPagination',
    'PAGE_SIZE': 10,  # 每页显示的条目数
}

2. 创建模型和序列化器

假设你有一个 Article 模型:

from django.db import models

class Article(models.Model):
    title = models.CharField(max_length=200)
    content = models.TextField()
    created_at = models.DateTimeField(auto_now_add=True)

    def __str__(self):
        return self.title

创建一个序列化器 ArticleSerializer

from rest_framework import serializers
from .models import Article

class ArticleSerializer(serializers.ModelSerializer):
    class Meta:
        model = Article
        fields = ['id', 'title', 'content', 'created_at']

3. 实现搜索和分页的 APIView

views.py 中,创建一个 ArticleSearchAPIView,并实现搜索和分页功能:

from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import status
from rest_framework.pagination import PageNumberPagination
from .models import Article
from .serializers import ArticleSerializer
from django.db.models import Q

class ArticleSearchAPIView(APIView):
    def get(self, request, *args, **kwargs):
        search_query = request.query_params.get('q', '')
        articles = Article.objects.filter(
            Q(title__icontains=search_query) | Q(content__icontains=search_query)
        )

        # 分页
        paginator = PageNumberPagination()
        paginator.page_size = request.query_params.get('page_size', 10)  # 允许客户端自定义每页大小
        result_page = paginator.paginate_queryset(articles, request)

        serializer = ArticleSerializer(result_page, many=True)
        return paginator.get_paginated_response(serializer.data)

4. 配置 URL

urls.py 中配置路由:

from django.urls import path
from .views import ArticleSearchAPIView

urlpatterns = [
    path('articles/search/', ArticleSearchAPIView.as_view(), name='article-search'),
]

5. 测试 API

启动 Django 开发服务器:

python manage.py runserver

然后你可以通过以下 URL 进行搜索和分页:

http://127.0.0.1:8000/articles/search/?q=your_search_query&page=2&page_size=5
  • q 是搜索关键字。
  • page 是请求的页码。
  • page_size 是每页显示的条目数(可选)。

6. 自定义分页器(可选)

如果你需要自定义分页器,可以创建一个自定义的分页类:

from rest_framework.pagination import PageNumberPagination

class CustomPagination(PageNumberPagination):
    page_size = 10
    page_size_query_param = 'page_size'
    max_page_size = 100

    def get_paginated_response(self, data):
        return Response({
            'links': {
                'next': self.get_next_link(),
                'previous': self.get_previous_link()
            },
            'count': self.page.paginator.count,
            'results': data
        })

然后在 ArticleSearchAPIView 中使用自定义分页器:

class ArticleSearchAPIView(APIView):
    pagination_class = CustomPagination

    def get(self, request, *args, **kwargs):
        search_query = request.query_params.get('q', '')
        articles = Article.objects.filter(
            Q(title__icontains=search_query) | Q(content__icontains=search_query)
        )

        paginator = self.pagination_class()
        result_page = paginator.paginate_queryset(articles, request)

        serializer = ArticleSerializer(result_page, many=True)
        return paginator.get_paginated_response(serializer.data)

总结

通过使用 DRF 的分页器,你可以轻松地在 APIView 中实现分页功能。你可以使用默认的 PageNumberPagination,也可以根据需要自定义分页器。这样,你的文章搜索接口将能够优雅地支持分页功能。