1,create优化

在serializer序列化中,我们通过创建序列化器对象的方式大大地简化了视图函数的代码,前端传入的数据通过反序列化操作进行了各种数据校验,代码如下:

  1. from django.http import JsonResponse
  2. from django.views import View
  3. from django.db import connection
  4. import json
  5. from .models import Projects
  6. from .serializers import ProjectSerializer
  7. class ProjectsPage(View):
  8. '''
  9. 类视图
  10. '''
  11. def post(self, request):
  12. input_data = json.loads(request.body)
  13. serializer_check_obj = ProjectSerializer(data=input_data)
  14. if not serializer_check_obj.is_valid():
  15. return JsonResponse({"code": 1, "res": "error", "msg": serializer_check_obj.errors})
  16. obj = Projects.objects.create(**serializer_check_obj.validated_data)
  17. serializer_obj = ProjectSerializer(instance=obj)
  18.      return JsonResponse(serializer_obj.data, status=201)
  • 从上面的代码可以看到,创建了两个序列化器的对象,一个serializer_check_obj用来进行反序列化参数校验,给instance传参,一个用来序列化输出。冗余
  • 我们可以去掉serializer_obj,然后调用serializer_check_obj的save()方法,save()方法会自动调用模型类对象中定义的create方法

    1. def post(self, request):
    2. input_data = json.loads(request.body)
    3. serializer_check_obj = ProjectSerializer(data=input_data)
    4. if not serializer_check_obj.is_valid():
    5. return JsonResponse({"code": 1, "res": "error", "msg": serializer_check_obj.errors})
    6. serializer_check_obj.save()
    7. return JsonResponse(serializer_check_obj.validated_data, status=201)

    模型类中的create方法需要提前定义,该方法是父类的create方法,我们可以进行重写,父类方法源码如下:
    DRF-Serializer视图优化 - 图1
    在序列化器类中重写父类的create方法,并返回模型类对象

    1. def create(self, validated_data):
    2. obj = Projects.objects.create(**validated_data)
    3. return obj

    在调用序列化器类对象的save()方法时,也可以传参,传参以关键字的方式传入,它会自动添加到create方法的validated_data中,我们可以根据这个参数去进行一些关联,如判断当前项目已登录,或者当前这个项目判断是哪个用户创建的

    2,update优化

    原先的写法

    1. def put(self, request, pk=None):
    2. if pk:
    3. update_data = json.loads(request.body)
    4. obj = Projects.objects.get(id=pk)
    5. serializer_check_obj = ProjectSerializer(data=update_data)
    6. if not serializer_check_obj.is_valid():
    7. return JsonResponse({"code": 1, "res": "error", "msg": serializer_check_obj.errors})
    8. obj.name = serializer_check_obj.validated_data.get('name') or obj.name
    9. obj.leader = serializer_check_obj.validated_data.get('leader') or obj.leader
    10. obj.programmer = serializer_check_obj.validated_data.get('programmer') or obj.programmer
    11. obj.tester = serializer_check_obj.validated_data.get('tester') or obj.tester
    12. obj.save()
    13. serializer_obj = ProjectSerializer(instance=obj)
    14. return JsonResponse(serializer_obj.data, status=201)

    同前面一样,创建了两个序列化器类的对象,可以对其进行合并,合并方式跟create有一些差别

  • 同时给模型类对象传入instance 和 data,之后调用save()方法,会默认去调用源码中的update方法

优化之后的代码

  1. def put(self, request, pk=None):
  2. if pk:
  3. update_data = json.loads(request.body)
  4. obj = Projects.objects.get(id=pk)
  5. serializer_obj = ProjectSerializer(data=update_data, instance=obj)
  6. if not serializer_obj.is_valid():
  7. return JsonResponse({"code": 1, "res": "error", "msg": serializer_obj.errors})
  8. serializer_obj.save()
  9. return JsonResponse(serializer_obj.data, status=201)

模型类中的update方法需要提前定义,该方法是父类的update方法,我们可以进行重写,父类方法源码如下:
DRF-Serializer视图优化 - 图2

  • 在序列化器类中重写父类的update方法,并返回模型类对象
    1. def update(self, instance, validated_data):
    2. # instance为待更新的模型类对象
    3. # validated_data参数为校验通过之后的数据
    4. # 必须将更新成功的模型类对象返回
    5. instance.name = validated_data.get('name') or instance.name
    6. instance.leader = validated_data.get('leader') or instance.leader
    7. instance.programmer = validated_data.get('programmer') or instance.programmer
    8. instance.tester = validated_data.get('tester') or instance.tester
    9. instance.save()
    10. return instance