DRF序列化器、模型层路由层、常用字段
DRF序列化器、模型层路由层、常用字段
-
序列化器-Serializer
# 序列化器的作用 1. 序列化,序列化器会把模型对象转换成字典,经过response以后变成json字符串 2. 反序列化,把客户端发送过来的数据,经过request以后变成字典,序列化器可以把字典转成模型 3. 反序列化,完成数据校验功能
-
序列化器的基本使用
序列化器的使用分两个阶段: 1.在客户端请求时,使用序列化器可以完成对数据的反序列化。 2.在服务器响应时,使用序列化器可以完成对数据的序列化。
-
视图层views.py
from django.shortcuts import render from app01 import models # 导入APIView模块 from rest_framework.views import APIView # 导入自定义序列化类 from app01.MySerializer import BookSerializer # 导入Response from rest_framework.response import Response class Bookser(APIView): # 查询全部数据 def get(self, request, *args, **kwargs): # 1.查询所有图书对象 book_list = models.Book.objects.all() # 2.序列化 引入自定义序列化类 instance 要序列化的对象 可以单个对象,可以多个, 多个要加many=True bs = BookSerializer(instance=book_list, many=True) # 3.传给前段 统一用Response 里面有一个data参数 return Response(data=bs.data) def post(self,request,*args,**kwargs): #1.反序列化接受的参数 前端传入的数据,在request.data中,是个字典 ser=BookSerializer(data=request.data) print(ser) #2.数据校验:如果是True,表示校验通过,直接保存 if ser.is_valid(): ser.save()# 调用保存,但是有问题,保存不了,一定要在序列化类中重写某个方法 return Response(ser.data) else: return Response(ser.errors) class BookDetailSer(APIView): # 查询单个字段 def get(self, request, pk): # 1.查询pk对应的数据对象 book_obj = models.Book.objects.filter(pk=pk).first() # 2.序列化 bs = BookSerializer(instance=book_obj) # 3.发送给前端 return Response(data=bs.data) def put(self,request, pk): #1.查找数据对象 book_obj=models.Book.objects.filter(pk=pk).first() #2.序列化数据对象 前端传入的数据,在request.data中,是个字典 ser=BookSerializer(instance=book_obj,data=request.data) #3.数据校验 记得重写uppdate方法 if ser.is_valid(): ser.save() return Response(ser.data) else: return Response(ser.errors) #删除后返回一个空的 def delete(self,request,pk): models.Book.objects.filter(pk=pk).delete() return Response()
-
序列化器文件serializer.py
#引入Serializer模块 from rest_framework import serializers #导入models from app01 import models from rest_framework.exceptions import ValidationError # 一定要继承一个序列化的基类 class BookSerializer(serializers.Serializer): # 你想序列化哪个字段,就写哪个 title = serializers.CharField(max_length=8,min_length=3,) price = serializers.IntegerField() publish = serializers.CharField(max_length=8,min_length=3) # 重写create,使它能够支持新增保存 (派生) def create(self, validated_data): #validated_data校验过后的数据 book=models.Book.objects.create(**validated_data) return book # 一定不要忘了return 对象,否则在视图类中用ser.data 就报错了 def update(self, instance, validated_data): instance.title=validated_data.get('title') instance.price=validated_data.get('price') instance.publish=validated_data.get('publish') instance.save() return # validate_字段名局部钩子 先走字段自己的,再走局部钩子 def validate_title(self,item): print(item) #检验规则 需要导入ValidationError if item.startswith('lv'): raise ValidationError('不能以lv开头') return item #先走局部再走全局 def validate(self, attrs): print(attrs) #验证 title和出版社不能相同 if attrs.get('title')==attrs.get('publish'): raise ValidationError('书名和出版社不能相同') return attrs
-
表模型层 models.py
from django.db import models # Create your models here. class Book(models.Model): title = models.CharField(max_length=16, default='好书') price = models.IntegerField(default=0) publish = models.CharField(max_length=32, default='奥特出版社')
-
路由层 urls.py
from django.contrib import admin from django.urls import path from app01 import views urlpatterns = [ path('admin/', admin.site.urls), path('books/',views.Bookser.as_view()), path('books/<int:pk>/', views.BookDetailSer.as_view()), #记得加/ ]
-
常用字段
字段 字段构造方式 BooleanField BooleanField() NullBooleanField NullBooleanField() CharField CharField(max_length=None, min_length=None, allow_blank=False, trim_whitespace=True) EmailField EmailField(max_length=None, min_length=None, allow_blank=False) RegexField RegexField(regex, max_length=None, min_length=None, allow_blank=False) SlugField SlugField(maxlength=50, min_length=None, allow_blank=False) 正则字段,验证正则模式 [a-zA-Z0-9-]+ URLField URLField(max_length=200, min_length=None, allow_blank=False) UUIDField UUIDField(format=’hex_verbose’) format: 1) 'hex_verbose'
如"5ce0e9a5-5ffa-654b-cee0-1238041fb31a"
2)'hex'
如"5ce0e9a55ffa654bcee01238041fb31a"
3)'int'
- 如:"123456789012312313134124512351145145114"
4)'urn'
如:"urn:uuid:5ce0e9a5-5ffa-654b-cee0-1238041fb31a"
IPAddressField IPAddressField(protocol=’both’, unpack_ipv4=False, **options) IntegerField IntegerField(max_value=None, min_value=None) FloatField FloatField(max_value=None, min_value=None) DecimalField DecimalField(max_digits, decimal_places, coerce_to_string=None, max_value=None, min_value=None) max_digits: 最多位数 decimal_palces: 小数点位置 DateTimeField DateTimeField(format=api_settings.DATETIME_FORMAT, input_formats=None) DateField DateField(format=api_settings.DATE_FORMAT, input_formats=None) TimeField TimeField(format=api_settings.TIME_FORMAT, input_formats=None) DurationField DurationField() ChoiceField ChoiceField(choices) choices与Django的用法相同 MultipleChoiceField MultipleChoiceField(choices) FileField FileField(max_length=None, allow_empty_file=False, use_url=UPLOADED_FILES_USE_URL) ImageField ImageField(max_length=None, allow_empty_file=False, use_url=UPLOADED_FILES_USE_URL) ListField ListField(child=, min_length=None, max_length=None) DictField DictField(child=) 常用字段参数
参数名称 作用 max_length 最大长度 min_lenght 最小长度 allow_blank 是否允许为空 trim_whitespace 是否截断空白字符 max_value 最小值 min_value 最大值 参数名称 作用 read_only(重要) 表明该字段仅用于序列化输出,默认False序列化 write_only(重要) 表明该字段仅用于反序列化输入,默认False 反序列化 required 表明该字段在反序列化时必须输入,默认True ,必须传 或者不传 default 反序列化时使用的默认值 allow_null 表明该字段是否允许传入None,默认False 必须传 可以传空 validators 该字段使用的验证器 error_messages 包含错误编号与错误信息的字典 label 用于HTML展示API页面时,显示的字段名称 help_text 用于HTML展示API页面时,显示的字段帮助提示信息 -
序列化器的反序列化
#post和put都是反序列化前端发过来的数据 def post(self,request,*args,**kwargs): #1.反序列化接受的参数 前端传入的数据,在request.data中,是个字典 ser=BookSerializer(data=request.data) #2.数据校验:如果是True,表示校验通过,直接保存 if ser.is_valid(): ser.save()# 调用保存,但是有问题,保存不了,一定要在序列化类中重写某个方法 return Response(ser.data) else: return Response(ser.errors) def put(self,request, pk): #1.查找数据对象 book_obj=models.Book.objects.filter(pk=pk).first() #2.序列化数据对象 前端传入的数据,在request.data中,是个字典 ser=BookSerializer(instance=book_obj,data=request.data) #3.数据校验 记得重写uppdate方法 if ser.is_valid(): ser.save() return Response(ser.data) else: return Response(ser.errors)
-
模型类序列化器(重要)ModelSerializer
相对于Serializer 不需要重写create和update #因为内部封装了这两个方法 序列化,不需要每个字段都写 class BookModelSerializer(serializers.ModelSerializer): class Meta: model=models.Book #跟那个表建立关系 # fields=['title','price'] #要序列化哪些字段 fields='__all__' #要序列化哪些字段 全部 #了解 # exclude=['title'] # 除了某个字段除外显示其他 # depth = 1 # 表关联 查询关联的表的信息 还是只显示id #校验规则 写在meta类里 额外给某些字段传参数 # extra_kwargs = {'title': {'max_length': 8, 'min_length': 3}, # 'price': {'min_value': 100}} #read_only 只读 只序列化 title 这个字段只序列化 #详细解释 :post请求 传参数时候title这个key传不传值都一样 不会用来写 给用户看 往外走 extra_kwargs = {'title': {'read_only':True}, 'price': {'write_only': True}} #write_only 只写 只反序列化price 这个字段只写 不做序列化 往数据库写 往里走 #校验规则 重写某个字段 写在外面 # title=serializers.CharField(max_length=8,min_length=3) # # #钩子 # def validate_price(self,price): # if price>300: # raise ValidationError('价格不能大于100') # return price