📌  相关文章
📜  在 Django REST Framework 中自定义过滤器

📅  最后修改于: 2022-05-13 01:54:51.726000             🧑  作者: Mango

在 Django REST Framework 中自定义过滤器

先决条件:在 API 中添加过滤 - Django REST 框架 [lin 需要发布的文章]

Django 过滤器有助于过滤查询集,以根据分配给过滤器字段的值检索相关结果。但是,如果用户想要检索给定范围内的详细信息怎么办。例如,用户需要根据价格范围获取机器人的详细信息。自定义过滤器的必要性来了。让我们创建一个自定义过滤器并将其应用于机器人模型,以便用户可以通过提供机器人类别名称、制造商名称、货币、制造日期范围和/或价格范围来检索机器人详细信息。

我们将创建一个名为RobotFilter类的新类,它是django_filters.FilterSet类的子类。让我们声明进口

Python3
from django_filters import FilterSet, AllValuesFilter
from django_filters import DateTimeFilter, NumberFilter


Python3
class RobotFilter(FilterSet):
    from_manufacturing_date = DateTimeFilter(field_name='manufacturing_date',
                                             lookup_expr='gte')
    to_manufacturing_date = DateTimeFilter(field_name='manufacturing_date',
                                           lookup_expr='lte')
    min_price = NumberFilter(field_name='price', lookup_expr='gte')
    max_price = NumberFilter(field_name='price', lookup_expr='lte')
    robotcategory_name = AllValuesFilter(field_name='robot_category__name')
    manufacturer_name = AllValuesFilter(field_name='manufacturer__name')
  
    class Meta:
        model = Robot
        fields = (
            'name',
            'currency',
            'from_manufacturing_date',
            'to_manufacturing_date',
            'min_price',
            'max_price',
            'robotcategory_name',
            'manufacturer_name',
            )


Python3
class RobotList(generics.ListCreateAPIView):
    queryset = Robot.objects.all()
    serializer_class = RobotSerializer
    name = 'robot-list'
    # customized filter class
    filter_class = RobotFilter
    search_fields = (
        '^name',
    )
    ordering_fields = (
        'price',
    )


现在,您可以在 RobotList 类之前添加以下代码。



蟒蛇3

class RobotFilter(FilterSet):
    from_manufacturing_date = DateTimeFilter(field_name='manufacturing_date',
                                             lookup_expr='gte')
    to_manufacturing_date = DateTimeFilter(field_name='manufacturing_date',
                                           lookup_expr='lte')
    min_price = NumberFilter(field_name='price', lookup_expr='gte')
    max_price = NumberFilter(field_name='price', lookup_expr='lte')
    robotcategory_name = AllValuesFilter(field_name='robot_category__name')
    manufacturer_name = AllValuesFilter(field_name='manufacturer__name')
  
    class Meta:
        model = Robot
        fields = (
            'name',
            'currency',
            'from_manufacturing_date',
            'to_manufacturing_date',
            'min_price',
            'max_price',
            'robotcategory_name',
            'manufacturer_name',
            )

我们来看看 RobotFilter 类中声明的属性。

  • from_manufacturing_date
  • 到_制造日期
  • 最低价格
  • 最大价格
  • 机器人类别名称
  • 生产商名称

from_manufacturing_date:它是一个django_filters.DateTimeFilter实例属性,用于过滤manufacturing_date 值大于或等于指定DateTime 值的机器人。在 DateTimeFilter 中,有两个名为field_namelookup_expr 的参数。 field_name 具有制造日期(用于过滤),并且“gte”(大于或等于)应用于 lookup_expr。

to_manufacturing_date:它是一个django_filters.DateTimeFilter实例属性,用于过滤manufacturing_date 值小于或等于指定DateTime 值的机器人。在 DateTimeFilter 中,有两个名为field_namelookup_expr 的参数。在field_name 中,我们提到了制造日期,而'lte'(小于或等于)应用于lookup_expr。

min_price:django_filters.NumberFilter实例属性,用于过滤价格值大于或等于指定价格值的机器人。

max_price:它是一个django_filters.NumberFilter实例属性,用于过滤价格值小于或等于指定价格值的机器人。

robotscategory_name:它是一个django_filters.AllValuesFilter实例属性,用于过滤机器人类别名称与指定字符串值匹配的机器人。您可以注意到,在提供给field_name的值中,robot_category 和 name 之间有一个双下划线 (__)。 field_name 使用 Django 双下划线将其读取为 RobotCategory 模型的名称字段。这有助于根据机器人类别名称而不是其 pk id 检索机器人的详细信息。

制造商名称:它是一个django_filters.AllValuesFilter实例属性,用于过滤制造商名称与指定字符串值匹配的机器人。 field_name 使用 Django 双下划线读取值 'manufacturer__name' 作为制造商模型的名称字段。这有助于根据制造商名称而不是其 pk id 检索机器人的详细信息。



RobotFilter类还定义了一个Meta内部类。这个类有两个属性modelfields 。模型属性指定要过滤的模型(机器人)。而且, fields 属性包含字段名称和过滤器名称(作为字符串元组)以包含在上述模型(机器人)的过滤器中。

让我们在RobotList类中使用RobotFilter类。代码如下

蟒蛇3

class RobotList(generics.ListCreateAPIView):
    queryset = Robot.objects.all()
    serializer_class = RobotSerializer
    name = 'robot-list'
    # customized filter class
    filter_class = RobotFilter
    search_fields = (
        '^name',
    )
    ordering_fields = (
        'price',
    )

让我们在制造日期内过滤机器人。 HTTPie 命令是

输出:

让我们根据机器人类别名称和制造商名称过滤机器人。 HTTPie 命令如下

输出:



让我们根据价格范围过滤机器人。 HTTPie 命令是

输出:

让我们使用可浏览的 API 功能过滤机器人。您可以浏览以下 URL 并单击过滤器按钮。

您可以填充值以针对机器人进行过滤。下面分享截图

单击提交按钮后,您将获得过滤后的结果。下面分享截图