DRF-序列化

作者: f050d162bcc1 | 来源:发表于2019-01-19 13:50 被阅读0次

序列化

  • 序列化有两大功能:请求数据的验证,对queryset的序列化

  • 创建URL

 url(r'^(?P<version>[v1|v2]+)/roles/$', views.RolesView.as_view()),
  • 编写视图(方法1)
class RolesView(APIView):
    def get(self, request, *args, **kwargs):
        roles = models.Role.objects.all().values('id', 'title')
        roles = list(roles)
        import json
        ret = json.dumps(roles)
        return HttpResponse(ret)
  • 浏览器效果
微信截图_20190119005034

DRF序列化

from rest_framework import serializers


class RolesSerializer(serializers.Serializer):
    # 必须给数据库的字段一致
    title = serializers.CharField()


class RolesView(APIView):
    def get(self, request, *args, **kwargs):
        roles = models.Role.objects.all()
        ser = RolesSerializer(instance=roles, many=True)
        import json
        return HttpResponse(json.dumps(ser.data))

自定义序列化

  • 创建URL
url(r'^(?P<version>[v1|v2]+)/userinfo/$', views.UserInfoView.as_view())
  • 创建视图
class UserInfoSerializer(serializers.Serializer):
    username = serializers.CharField()
    password = serializers.CharField()



class UserInfoView(APIView):
    def get(self, request, *args, **kwargs):
        users = models.UserInfo.objects.all()
        ser = UserInfoSerializer(users, many=True)
        import json
        return HttpResponse(json.dumps(ser.data))
  • 假设我需要把用户类型也显示出来
class UserInfoSerializer(serializers.Serializer):
    user_type = serializers.IntegerField()
    ...
微信截图_20190119012852
  • 显示具体choice中文
class UserInfoSerializer(serializers.Serializer):
    xxxx = serializers.IntegerField(source='user_type')
    oooo = serializers.CharField(source='get_user_type_display')
    username = serializers.CharField()
    password = serializers.CharField()
微信截图_20190119014314
  • 显示指定内容
class UserInfoSerializer(serializers.Serializer):
    ...
    gp = serializers.CharField(source="group.id")
    gp2 = serializers.CharField(source="group.title")
微信截图_20190119015235
class UserInfoSerializer(serializers.Serializer):
    xxxx = serializers.IntegerField(source='user_type')
    oooo = serializers.CharField(source='get_user_type_display')
    username = serializers.CharField()
    password = serializers.CharField()
    gp = serializers.CharField(source="group.id")
    gp2 = serializers.CharField(source="group.title")
    rls = serializers.SerializerMethodField()  # 自定义显示

    def get_rls(self, row):  # row当前行的对象
        return [
            {
                'id': 1,
                'title': '老司机'
            }
        ]
微信截图_20190119020029
class UserInfoSerializer(serializers.Serializer):
    xxxx = serializers.IntegerField(source='user_type')
    oooo = serializers.CharField(source='get_user_type_display')
    username = serializers.CharField()
    password = serializers.CharField()
    gp = serializers.CharField(source="group.id")
    gp2 = serializers.CharField(source="group.title")
    rls = serializers.SerializerMethodField()  # 自定义显示

    def get_rls(self, row):  # row当前行的对象
        role_obj_list = row.roles.all()

        ret = []
        for item in role_obj_list:
            ret.append({
                'id': item.id,
                'title': item.title
            })

        return ret
微信截图_20190119021006

ModelSerializer

class UserInfoSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.UserInfo
        fields = "__all__"
微信截图_20190119022808
class UserInfoSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.UserInfo
        fields = ["id", "username"]
微信截图_20190119022950
class UserInfoSerializer(serializers.ModelSerializer):
    oooo = serializers.CharField(source='get_user_type_display')

    class Meta:
        model = models.UserInfo
        fields = ["id", "username",'oooo']
微信截图_20190119023118
class UserInfoSerializer(serializers.ModelSerializer):
    oooo = serializers.CharField(source='get_user_type_display')
    rls = serializers.SerializerMethodField()

    class Meta:
        model = models.UserInfo
        fields = ["id", "username", 'oooo', 'rls']

    def get_rls(self, row):
        role_obj_list = row.roles.all()

        ret = []
        for item in role_obj_list:
            ret.append({
                'id': item.id,
                'title': item.title
            })
        return ret
微信截图_20190119023440

DRF序列化深度控制

class UserInfoSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.UserInfo
        fields = "__all__"
微信截图_20190119110515
# 官方建议depth不要超过10层,个人建议撑死3层
class UserInfoSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.UserInfo
        fields = "__all__"
        depth = 1  # 深度控制,数字表示往里面拿的层数,写1就为1层,但是层数越多,效率越慢
微信截图_20190119110708

序列化生成hypermed(给url)

  • 编写URL
 url(r'^(?P<version>[v1|v2]+)/group/(?P<pk>\d+)/$', views.GroupfoView.as_view(),name='gp')
  • 查看组的详细
class GroupSerializer(serializers.ModelSerializer):
    class Meta:
        model = models.UserGroup
        fields = "__all__"


class GroupfoView(APIView):
    def get(self, request, *args, **kwargs):
        pk = kwargs.get('pk')
        obj = models.UserGroup.objects.filter(pk=pk).first()
        import json
        ser = GroupSerializer(instance=obj, many=False)
        ret = json.dumps(ser.data)
        return HttpResponse(ret)
  • 改进
class UserInfoView(APIView):
    def get(self, request, *args, **kwargs):
        ...
        ser = UserInfoSerializer(users, many=True,context={'request': request})
        ...
class UserInfoSerializer(serializers.ModelSerializer):
    # 帮我们反向生成URL,相当于我们给了group一个id,它帮我们反向生成一个url
    group = serializers.HyperlinkedIdentityField(view_name='gp')

    class Meta:
        model = models.UserInfo
        fields = "__all__"
        depth = 0
微信截图_20190119113108

源码流程

 def __new__(cls, *args, **kwargs):
        # We override this method in order to automagically create
        # `ListSerializer` classes instead when `many=True` is set.
        # many=True,对Queryset进行处理
        if kwargs.pop('many', False):
            return cls.many_init(*args, **kwargs)
        # many=False,对对象进行处理
        return super(BaseSerializer, cls).__new__(cls, *args, **kwargs)

序列化验证

  • 编写URL
url(r'^(?P<version>[v1|v2]+)/usergroup/$', views.UserGroupView.as_view(), name='ugp'),
  • 编写视图
class UserGroupView(APIView):
    def post(self, request, *args, **kwargs):
        print(request.data)
        return HttpResponse("提交数据")
  • post提交数据
微信截图_20190119132729 微信截图_20190119132812
  • 验证
class UserGroupSerializer(serializers.Serializer):
    title = serializers.CharField()


class UserGroupView(APIView):
    def post(self, request, *args, **kwargs):
        ...
        ser = UserGroupSerializer(data=request.data)
        if ser.is_valid():
            print(ser.validated_data)
        else:
            print(ser.errors)
        ...
微信截图_20190119133328 微信截图_20190119133449 微信截图_20190119133519 微信截图_20190119133549
  • 自定义错误信息
微信截图_20190119133856

相关文章

网友评论

    本文标题:DRF-序列化

    本文链接:https://www.haomeiwen.com/subject/bltzdqtx.html