drf序列化组件

1.rest-framework序列化之Serializer

rest-framework序列化之Serializer步骤
    1. 创建一个类,继承Serializer
    2. 在类中写要序列化的字段
'''
class BookSerializer(serializers.Serializer):
    # 序列化表中的某几个字段 固定写法
    nid = serializers.CharField()
    name = serializers.CharField()
    title = serializers.CharField(source='name')
    price = serializers.CharField()
    publish = serializers.CharField(source='publish.email')
'''
    3. 在View.py中使用
'''
    # 使用序列化
    def get(self, request):
        response = {'status': 100, 'msg': '获取成功'}
        book_list = Book.objects.all()
        # 实力化BookSerializer, 将要实力化的数据传入(Queryset对象)
        # 要是用序列化一定要加many=True
        book_ser = BookSerializer(book_list, many=True)
        response['data'] = book_ser.data
        return Response(response)
'''

2. source的用法

  1. 指定字段 2. 指定方法 3.深度查询(跨表)

3. rest-framework序列化之ModelSerializer

# 继承ModelSerializer,可以直接指定要序列化的表模型
1. 写一个类, 继承ModelSerializer
2. 在类内部写
class BookSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.Book
            # 指定要序列化的字段
            # fields=['nid','name']
            # __all__显示全部内容
            field ='__all__'
            # 筛选(注意,不能跟fields连用)
            exclude = ['name', 'price']
            # 深度
            depth = 1
    重写属性  
    publish字段,返回出版社的所有信息,包括id,name,email。。。。
    #SerializerMethodField配合一个方法,方法的返回值会付给publish
    publish=serializers.SerializerMethodField()
    def get_publish(self,obj):
        # print(type(obj))
        # print(obj)
        return {'id':obj.publish.pk,'name':obj.publish.name}

4. 序列化单条数据

  book_ser=BookSerializer(instance=book,many=False)

5. 反序列化之局部和全局钩子(序列化的类一定是继承ModelSerializer的类)

    def validate_name(self, value):
    if value.startswith('sb')
        raise ValidationError('书名不能以s开头)
    else:
        return value
    #全局钩子函数,对全局字段进行校验
    def validate(self,atrr):
        # print(atrr)
        name=atrr.get('name')
        price=atrr.get('price')
        if name != price:
            raise ValidationError('错了')
        else:
            return a

 6. 源码及实现

'''
反序列化局部钩子函数源码:
    1. is_valid
    2. self.run_validation-(执行Serializer的run_validation)
    3. self.to_internal_value(data) 
    4.(执行Serializer的run_validation:485行)
many=True时和many=False时,生成的其实不是一个对象
    序列化组件,先调用__new__方法,如果many=True,生成ListSerializer对象,如果为False,生成Serializer对象
序列化组件source源码部分
    序列化对象.data方法--调用父类data方法---调用对象自己的to_representation(自定义的序列化类无此方法,去父类找)
    Aerializer类里有to_representation方法,for循环执行attribute = field.get_attribute(instance)
    再去Field类里去找get_attribute方法,self.source_attrs就是被切分的source,然后执行get_attribute方法,source_attrs
    当参数传过去,判断是方法就加括号执行,是属性就把值取出来

'''
学习,学习,学习! 学习是为了更好的未来,不要让别人瞧不起你,加油!!!
原文地址:https://www.cnblogs.com/yangyufeng/p/10600925.html