使用 Django Rest Framwork / Django Filter 进行分面

Jul*_*ian 6 django django-filter django-rest-framework

亲爱的溢出者们,

\n

I\xe2\x80\x99m 目前正在使用 Django Filter 构建基于 Django Rest Framework 的 API。

\n

搜索、过滤和排序工作得相当好,尽管我想知道过滤器方面。

\n

想象一下,\xe2\x80\x99s 有一个 \xe2\x80\x9cPerson\xe2\x80\x9d 模型,而你\xe2\x80\x99d 希望允许用户按人员\xe2\x80\x99 名称的首字母进行过滤。您不希望用户遇到 \xe2\x80\x99cno 结果\xe2\x80\x9d 的情况,因此您只想建议与至少一个人匹配的字母。

\n

为每个过滤器提供选择列表(方面)的好方法是什么?\n使用仅提供选择的不同端点是否有意义?\n对我来说,在 FilterSet 子类中声明方面是正确的,因为它\xe2\x80\x99是与过滤器相关的任何事情发生的地方。

\n

期待您的评论!

\n

朱利安

\n

PS:通常,我在这种情况下使用 ElasticSearch,但我想知道在普通 DRF/DF 中是否有\xe2\x80\x99s 惯用的解决方案。

\n
# models.py\n\nfrom django.db import models\n\nclass Person(models.Model):\n    name = models.CharField(max_length=200)\n\n\n# filters\nfrom django_filters import rest_framework as filters\nfrom django.db.models.functions import Substr\n\n\ndef get_first_letter_choices():\n    # Create choices\n    letters = Person.objects \\\n        .all() \\\n        .annotate(first_letter=Substr('name', 1, 1)) \\\n        .values_list("first_letter", flat=True) \\\n        .distinct()\n        \n    return [(letter, letter, ) for letter in letters]\n\nclass PersonFilterSet(filters.FilterSet):\n    first_letter = filters.ChoiceFilter(\n        choices=get_first_letter_choices,\n        field_name="name",\n        lookup_expr="startswith"\n    )\n\n# DRF Views/Serializers\n# serializers.py\nfrom rest_framework import serializers\n\nclass PersonSerializer(serializers.ModelSerializer):\n    class Meta:\n        model = Person\n        fields = ["name", ]\n\n\n# views.py\nfrom rest_framework import ListAPIView\n\nclass PersonsIndex(ListAPIView):\n    filterset_class = PersonFilterSet\n    serializer_class = PersonSerializer\n\n    def get_queryset(self):\n        return Person.objects.all()\n\n
Run Code Online (Sandbox Code Playgroud)\n

我尝试使用不同的端点并使用包含选择字段的自定义序列化器,但感觉就像我\xe2\x80\x99m 与 DRF/DF 作斗争。

\n