【问题标题】:How to filter relationships based on their fields in response using Django REST Framework如何使用 Django REST 框架根据字段过滤关系以响应响应
【发布时间】:2020-04-29 07:19:11
【问题描述】:

我有三个模型:House、Resident、Car。 每所房子都有许多居民(一对多)。每个居民有 0 或 1 辆汽车(一对一)。 对于我的前端,我想显示一所房子里所有有车的居民。 Django Rest Framework 建议使用过滤,但这仅适用于顶层。比如我的HouseDetailView(generics.RetrieveAPIView),只能修改House模型本身的queryset。我希望能够修改 Resident (resident_queryset.exclude(car=None)) 的查询集。

class HouseDetailView(generics.RetrieveAPIView):
  queryset = House.objects.all()
  serializer_class = HouseSerializer

我可以/应该在一个请求中完成这一切吗? 查询参数是我唯一的过滤方式吗?

【问题讨论】:

  • 你能分享你的models.py吗
  • House 与 House 有 name,Resident 与 House 有 nameForeignKey,Car 与 Resident 有 nameOneToOne 关系。

标签: django django-rest-framework django-filter serialization


【解决方案1】:
# If you want to display all the residents of a house that have a car, then you should query the car model


class CarDetailView(generics.RetrieveAPIView):
    queryset = Car.objects.all()
    serializer_class = CarSerializer


serializers.py

class CarSerializer(serializers.ModelSerializer):

    # get the resident details (name)
    resident_name = serializers.SerializerMethodField('get_resident_name')

    def get_resident_name(self, obj):
        return obj.resident.name


    class Meta:
        model = Car
        fields = ("name", "resident_name")

【讨论】:

    【解决方案2】:

    您可以使用Prefetch过滤相关对象:

    from django.db.models import Prefetch
    
    class HouseDetailView(generics.RetrieveAPIView):
      serializer_class = HouseSerializer
    
      def get_queryset(self):
          return House.objects.prefetch_related(Prefetch('resident_set', queryset=Resident.objects.exclude(car__isnull=True)))
    

    注意resident_setResident 模型的反向名称,根据related_name 参数,您可能会有所不同。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-06-17
      • 1970-01-01
      • 2020-05-29
      • 2017-09-23
      • 2021-11-05
      • 2020-03-01
      • 1970-01-01
      • 2017-01-12
      相关资源
      最近更新 更多