Django嵌套序列化器实现LEFT JOIN效果 嵌入客户关联订单返回方法
实现步骤
你只需要修改序列化器添加订单自定义字段,同时优化视图的查询逻辑避免N+1性能问题即可,具体修改如下:
1. 修改 serializer.py
新增SerializerMethodField类型的orders字段,自定义方法将订单转换为你需要的字典格式:
from rest_framework import serializers # 导入你的模型 from .models import MailingList, Order class CustomerSerializer(serializers.ModelSerializer): passport = serializers.CharField(source='customer.passport_number') # 把字段名改成name匹配你期望的返回格式,也可以保留customer_name自行调整 name = serializers.CharField(source='customer.name') # 新增订单字段 orders = serializers.SerializerMethodField() def get_orders(self, obj): # 遍历客户所有订单,组装为{订单ID: 商品名}的字典 return {str(order.id): order.item.name for order in obj.customer.order_set.all()} class Meta: model = MailingList # 新增orders到字段列表 fields = ['passport', 'name', 'orders']
2. 修改 views.py
调整预取逻辑,提前加载关联的订单、商品数据,避免大量重复查询数据库:
from django.db.models import Prefetch from rest_framework import viewsets from rest_framework.response import Response # 导入你的模型和序列化器 from .models import MailingList, Customer, Order from .serializer import CustomerSerializer class CustomerViewSet(viewsets.ViewSet): def list(self, request): queryset = MailingList.objects.filter(some_filters).prefetch_related( Prefetch( 'customer', queryset=Customer.objects.prefetch_related( Prefetch('order_set', queryset=Order.objects.select_related('item')) ) ) ) serializer = CustomerSerializer(queryset, many=True) return Response(serializer.data)
修改完成后返回的格式就和你期望的一致了,没有订单的客户会自动返回空的orders字典。
内容的提问来源于stack exchange,提问作者Otieno
相关产品推荐
相关产品推荐

