ModelSerializer序列化与反序列化

ModelSerializer序列化与反序列化(重点)

 视图类
# 单查群查

class UserV3APIView(APIView):
# 单查群查
def get(self, request, *args, **kwargs):
pk = kwargs.get('pk')
if pk:
user_obj = models.User.objects.filter(is_delete=False, pk=pk).first()
if not user_obj:
return Response({
'status': 1,
'msg': 'pk error',
}, status=400)

user_ser = serializers.UserModelSerializer(user_obj, many=False)
return Response({
'status': 0,
'msg': 'ok',
'results': user_ser.data
})
else:
user_query = models.User.objects.filter(is_delete=False).all()

user_ser = serializers.UserModelSerializer(user_query, many=True)

return Response({
'status': 0,
'msg': 'ok',
'results': user_ser.data
})

# 单增
def post(self, request, *args, **kwargs):
user_ser = serializers.UserModelSerializer(data=request.data)
if user_ser.is_valid():
# 入库
user_obj = user_ser.save()
return Response({
'status': 0,
'msg': 'ok',
'results': serializers.UserModelSerializer(user_obj).data
})
else:
return Response({
'status': 1,
'msg': user_ser.errors,
})

 序列化类

 1 class UserModelSerializer(serializers.ModelSerializer):
 2     # 第一种自定义序列化字段:该字段必须在fields中设置
 3     # gender = serializers.SerializerMethodField()
 4     # def get_gender(self, obj):
 5     #     return obj.get_sex_display()
 6 
 7     # 自定义反序列化字段同Serializer类,且规则只能在此声明中设置,或是在钩子中设置,
 8     #       在extra_kwargs中对其设置的无效
 9     # 注:自定义反序列化字段与系统字段,设置规则一样,所以必须设置 write_only
10     re_password = serializers.CharField(min_length=3, max_length=16, write_only=True)
11 
12     class Meta:
13         model = models.User
14         # fields采用 插拔式 设置所有参与序列化与反序列化字段
15         fields = ('username', 'gender', 'icon', 'password', 'sex', 're_password')
16         extra_kwargs = {
17             'username': {  # 系统字段不设置read_only和write_only,默认都参加
18                 'min_length': 3,
19                 'max_length': 10,
20                 'error_messages': {
21                     'min_length': '太短',
22                     'max_length': '太长'
23                 }
24             },
25             'gender': {
26                 'read_only': True,  # 自定义的序列化字段默认就是read_only,且不能修改,可以省略
27             },
28             'password': {
29                 'write_only': True,
30             },
31             'sex': {  # 像sex有默认值的字段,为选填字段('required': True可以将其变为必填字段)
32                 'write_only': True,
33                 # 'required': True
34             }
35         }
36 
37     # 局部全局钩子同Serializer类,是与 Meta 同缩进的
38     def validate_username(self, value):
39         if 'g' in value.lower():
40             raise serializers.ValidationError('名字中不能有g')
41         return value
42 
43     def validate(self, attrs):
44         password = attrs.get('password')
45         re_password = attrs.pop('re_password')
46         if password != re_password:
47             raise serializers.ValidationError({'re_password': '两次密码不一致'})
48         return attrs
49 
50     # create和update方法不需要再重写,ModelSerializer类已提供,且支持所有关系下的连表操作

模型类

 1 class UserV3APIView(APIView):
 2 
 3 
 4 """ ModelSerializer类序列化与反序列化总结
 5 1)序列化类继承ModelSerializer,所以需要在配置类Meta中进行配置
 6 2)model配置:绑定序列化相关的Model表
 7 3)fields配置:采用 插拔式 设置所有参与序列化与反序列化字段
 8 4)extra_kwargs配置:
 9     划分系统字段为三种:只读(read_only)、只写(write_only)、可读可写(不设置)
10     字段是否必须:required
11     选填字段:在extra_kwargs进行配置,但不设置required,且有默认值
12 5)自定义序列化字段:
13     第一种(不提倡):在序列化类中用SerializerMethodField()来实现
14     第二种(提倡):在模型类中用@property来实现,可插拔
15 6)自定义反序列化字段:
16     同Serializer类,且规则只能在此声明中设置,或是在钩子中设置,在extra_kwargs中对其设置的无效
17     自定义反序列化字段与系统字段,设置规则一样,所以必须设置 write_only
18 7)局部钩子,全局钩子同Serializer类
19 8)不需要重写create和update方法
20 """
21 
22 from django.db import models
23 
24 
25 class User(models.Model):
26     SEX_CHOICES = (
27         (0, ''),
28         (1, ''),
29     )
30 
31     username = models.CharField(max_length=64, verbose_name='用户名', blank=True, unique=True)
32     password = models.CharField(max_length=64, verbose_name='密码')
33     sex = models.IntegerField(choices=SEX_CHOICES, default=0, verbose_name='性别')
34     img = models.ImageField(upload_to='img', default='img/default.png', verbose_name='头像')
35     # 开发中,数据不会直接删除,通过字段控制
36     is_delete = models.BooleanField(default=False, verbose_name='是否注销')
37     # 数据库数据入库,一般都会记录该数据第一次入库时间,有时候还会记录最后一次更新时间
38     created_time = models.DateTimeField(auto_now_add=True, verbose_name='创建时间')
39 
40     # 第二种自定义序列化字段(插拔式,提倡使用)
41     @property
42     def gender(self):
43         return self.get_sex_display()
44 
45     @property
46     def icon(self):
47         from django.conf import settings
48         return '%s%s%s' % (settings.BASE_URL, settings.MEDIA_URL, self.img)
49 
50     class Meta:  # 配置类,给所属类提供配置信息
51         db_table = 'old_boy_user'
52         verbose_name_plural = '用户表'
53 
54     def __str__(self):  # 不要在这里进行连表操作,比如admin页面可能会崩溃
55         return self.username

 

posted @ 2021-07-07 17:29  代码歌  阅读(234)  评论(0)    收藏  举报