drf——序列化之source(了解)、定制字段的两种方式(重要)、多表关联反序列化保存、反序列化字段校验、ModelSerializer使用

1 序列化高级用法之source(了解)

# 1.创建了5个表(图书管理的5个)
# 2.对book进行序列化

# 总结:source的用法
	1.修改前端看到的字段key值--->source指定的必须是对象的属性
    	book_name = serialiazers.CharField(source='name')
    2.修改前端看到的value值 ---> source指定的必须是对象的方法
    	表模型中写方法
        def sb_name(self):
            return self.name = '_sb'
        序列化类中 
        	book_name = serializers.CharField(source='sb_name')
            
    3.可以关联查询(得有关联关系)
    	publish_name = serializers.CharField(source='publish.name')

2 序列化高级用法之定制字段的两种方式(非常重要)

# 方式一:在序列化类中写
	1.写一个字段 对应的字段类是:SerializerMethodField
    2.必须对应一个get_字段名的方法 方法必须接收一个obj 返回什么 这个字段对应的值就是什么
    
# 方式二:在模型层中写
	1.在表模型中写一个方法(可以使用:property),方法有返回值(字典,字符串,列表)
    2.在序列化类中 使用DictField,CharField,ListField

2.1在序列化类中写

class BookSerializer(serializer.Serializer):
    name = serializer.CharField()
    price = serializers.CharField()
    # 拿出出版社的id和名字和addr,放到一个字典中
    # 方式一:SerializerMethodField来定制,如果写了这个,必须配合一个方法get_字段名,这个方法返回什么,这个字段的值就是什么
    publish_detail = serializers.SerializerMethodField()
    
    def get_publish_detail(self,book):
        # print(obj) # 要序列化的book对象
        return {'id': book.publish.pk, 'name': book.publish.name, 'addr': book.publish.addr}
    
    # 练习:拿出所有作者的信息--》多条 [{'name':'','phone':''},{}]
    author_list = serializers.SerializerMethodField()
    
    def get_author_list(self,book):
        l = []
        for item in book.authors.all()
        	l.append({'id': author.pk, 'name': author.name, 'phone': author.phone, 'age': author.author_detail.age})
        return l

2.2表模型中写

############################### 序列化类 #############################
class BookSerializer(serializers.Serializer):
    name = serializers.CharField()
    price = serializers.CharField()
    # 1.序列化类中这样写
    # 2.到模型表中写一个方法 方法名必须叫publish_detail 这个方法返回什么 这个字段的value就是什么
    publish_detail = serializers.DictField()
    author_list = serializers.ListField()
   
################################ 表模型 ###########################
class Book(models.Model):
    name = models.CharField(max_length=32)
    price = models.CharField(max_length=32)
    publish = models.ForeignKey(to='Publish', on_delete=models.SET_NULL, null=True)
    authors = models.ManyToManyField(to='Author')

    @property
    def publish_detail(self):
        return {'id': self.publish.pk, 'name': self.publish.name, 'addr': self.publish.addr}

    def author_list(self):
        l = []
        for author in self.authors.all():
            l.append({'id': author.pk, 'name': author.name, 'phone': author.phone, 'age': author.author_detail.age})
        return l

3 多表关联反序列化保存

#序列化和反序列化 用的同一个序列化类
	序列化的字段有:name,price ,   publish_detail,author_list
    反序列化字段:name,price    ,publish,author

3.1反序列化之保存

视图类

class BookView(APIView):
    def post(self, request):
        ser = BookSerialzier(data=request.data)
        if ser.is_valid():
            ser.save()
            return Response({'code': 100, 'msg': '成功'})
        else:
            return Response({'code': 100, 'msg': ser.errors})

序列化类

class BookSerialzier(serializers.Serializer):
    # 即用来做序列化,又用来做反序列化
    name = serializers.CharField(max_length=8)
    price = serializers.CharField()

    # 这俩,只用来做序列化
    publish_detail = serializers.DictField(read_only=True)
    author_list = serializers.ListField(read_only=True)

    # 这俩,只用来做反序列化
    publish_id = serializers.IntegerField(write_only=True)
    authors = serializers.ListField(write_only=True)

    def create(self, validated_data):  # {name:西游记,price:88,publish:1,authors:[1,2]
        authors = validated_data.pop('authors')
        book = Book.objects.create(**validated_data)
        book.authors.add(*authors)
        book.save()
        return book

3.2反序列化之修改

视图类

class BookDetailView(APIView):

    def put(self, request,pk):
        book=Book.objects.get(pk=pk)
        ser = BookSerialzier(data=request.data,instance=book)
        if ser.is_valid():
            ser.save()
            return Response({'code': 100, 'msg': '更新成功'})
        else:
            return Response({'code': 100, 'msg': ser.errors})

序列化类

class BookSerialzier(serializers.Serializer):
    # 即用来做序列化,又用来做反序列化
    name = serializers.CharField(max_length=8)
    price = serializers.CharField()

    # 这俩,只用来做序列化
    publish_detail = serializers.DictField(read_only=True)
    author_list = serializers.ListField(read_only=True)

    # 这俩,只用来做反序列化
    publish_id = serializers.IntegerField(write_only=True)
    authors = serializers.ListField(write_only=True)
    
    def update(self,instance,validated_data):
        authors = validated_data.pop('authors')
        for item in validated_data:
            setattr(instance,item,validated_data['item'])
        instance.authors.set(authors)
        instance.save()
        return instance

4 反序列化字段校验其他

# 视图类中调用:ser.is_valid()--->触发数据的校验
	4层
    	-字段自己的:max_length,required。。。
        -字段自己的:配合一个函数name = serializers.CharField(max_length=8,validators=[xxx])
        -局部钩子
        -全局钩子

5 ModelSerializer使用

# 之前写的序列化类 继承了Serializer 写字段 跟表模型没有必然联系
class XXSerializer()
	id=serializer.CharField()
	name=serializer.CharField()
    
 XXSerialzier既能序列化Book,又能序列化Publish

# 现在学的ModelSerializer,表示跟表模型一一对应,用法跟之前基本类似

    1 写序列化 继承ModelSerializer
    2 在序列化类中 再写一个类 必须交
    	class Meta:
            model=表模型
            fields=[]  # 要序列化的字段
     3 可以重写字段 一定不要放在class Meta下
    	定制字段 跟上面一样
     4 自定制的字段 一定要在fields中注册一下 
     5 class Meta: 有个extra_kwargs 为某个字段定制字段参数
     6 局部钩子 全局钩子 完全一致
     7 大部分情况下 不需要重写 create和update了
本文转载于网络 如有侵权请联系删除

相关文章

  • 编写一个程序,将 a.txt文件中的单词与b.txt文件中的单词交替合并到c.txt 文件中,a.txt文件中的单词用回车符分隔,b.txt文件中用回车或空格进行分隔

    importjava.io.File; importjava.io.FileNotFoundException; importjava.io.FileReader; importjava.io.FileWriter; importjava.io.IOException; publicclassnewManagerFile{ Stringwords[]; intpos=0; publicnewManagerFile(StringfileName,charspilt[])throwsException{ Filefile=newFile(fileName); FileReaderfr=newFileReader(file); charbuf[]=newchar[(int)file.length()]; intlen=fr.read(buf); StringbufString=newString(buf,0,len); StringBuffertemp=newStringBuffer(""); temp.append(spilt[0]

  • 【每日SQL打卡】​​​​​​​​​​​​​​​DAY 14丨报告的记录 I【难度简单】

    难度简单SQL架构动作表:Actions+---------------+---------+ | Column Name   | Type    | +---------------+---------+ | user_id       | int     | | post_id       | int     | | action_date   | date    |  | action        | enum    | | extra         | varchar | +---------------+---------+ 此表没有主键,所以可能会有重复的行。 action 字段是 ENUM 类型的,包含:('view', 'like', 'reaction', 'comment', 'report', 'share') extra 字段是可选的信息(可能为 null),其中的信息例如有:1.报告理由(a reason for report) 2.反应

  • facet_share {ggpol} 轴共享分面

    #install.packages("ggpol") library(ggpol)复制区间高亮标记#geom_tshighlight可以用来高亮时间序列中的一个时段 ggplot(economics,aes(x=date,y=unemploy))+ geom_line()+ geom_tshighlight( aes(xmin=as.Date("01/01/1990",format="%d/%m/%Y"), xmax=as.Date("01/01/2000",format="%d/%m/%Y")), alpha=0.005,fill="yellow")+ ggtitle(label="geom_tshighlight可以用来高亮时间序列中的一个时段") 复制半箱线图和一半jitter散点图#geom_boxjitter用于绘制混合的箱线图: #一半箱线图和一半jitter散点图,以及可选的误差线。 df<-data.frame( score=

  • 百亿关系链,架构如何设计?

    文章较长,听我娓娓道来。粉丝与关注,社交好友,都是典型的“多对多关系”的业务,这类业务的核心服务是好友中心,当关系链达到百亿之后,好友中心架构设计要考虑哪些因素,是本文将要分享的内容。什么是“多对多”关系?所谓的“多对多”,来自数据库设计中的“实体-关系”ER模型,用来描述实体之间的关联关系,一个学生可以选修多个课程,一个课程可以被多个学生选修,这里学生与课程时间的关系,就是多对多关系。什么是好友关系?好友关系主要分为两类:(1)弱好友关系;(2)强好友关系;两类都有典型的互联网产品应用。什么是弱好友关系?弱好友关系的建立,不需要双方彼此同意:用户A关注用户B,不需要用户B同意,此时用户A与用户B为弱好友关系,对A而言,他多“关注”了一个人,对B而言,他多了一个“粉丝”。微博粉丝是一个典型的弱好友关系应用。什么是强好友关系?强好友关系的建立,需要好友关系双方彼此同意:用户A请求添加用户B为好友,用户B同意,此时用户A与用户B则互为强好友关系,即A是B的好友,B也是A的好友。QQ好友是一个典型的强好友关系应用。什么是好友中心?好友中心是一个典型的多对多业务,一个用户可以添加多个好友,也可

  • 使用码云新建、推拉第一个项目文件

    一、新建git仓库准备工作本地电脑安装git。可通过git--version查看版本,确保本机已有git。新建一个码云账户,注意区分账户姓名(用户名)以及个人空间地址。如下图:图:区分用户名/个人空间地址 1在码云新建一仓库,可以先在readme中填写一些内容。图:新建仓库图片2在本地新建一个文件夹(你的项目文件夹),准备与该仓库进行关联。图:本地文件夹3打开命令行工具,切换到该文件夹目录下,输入下列命令。gitinit//初始化本地仓库 gitremoteaddoriginhttps://gitee.com/空间地址名字/项目名字.git//关联你的码云仓库 gitpulloriginmaster//拉文件首次拉,拉下readme复制注:简简单单,只有一个分支,后续完善。二、继续写代码这是一个漫长的过程,加油。三、写完推代码推之前先检查分支以及仓库状态(是否有其他更新) gitbranch gitpull//如有修改,此时已经同步到你本地复制然后再推自己的文件gitstatus//查看自己修改的文件 gitadd.//提交所有 gitstatus//再次查看 gitcommit-m“

  • Sentinel 集群限流设计原理

    1、集群限流使用场景2、集群限流与单机限流的异同思考3、探究集群限流实现原理3.1ClusterBuilderSlot详解在对一个资源进行流控规则判断时,首先将进入到NodeSelectorSlot,然后就会进入到ClusterBuilderSlot,为了与单机限流模式,介绍ClusterBuilderSlot时与NodeSelectorSlot进行一个对比。NodeSelectorSlot的核心实现截图如下所示:温馨提示:从该系列之前的文章也能得知,一个资源对应的一个NodeSelectorSlot实例,即多线程访问一个资源时,都会调用同一个NodeSelectorSlot实例。NodeSelectorSlot的关键点如下:Map<String,DefaultNode>map 在NodeSelectorSlot中是以contextId为维度进行缓存的,例如官方给出的Dubbo适配方法,contexId为dubbo服务的全路径名。即Dubbo的入口节点对应的缓存Key为context id。fireEntry的node参数 由于NodeSelectorSlot是第一个过滤器

  • 程序员并不适合创业,请不要搞什么 “无脑创业崇拜”

    题图:fromZoommy 我曾写过一篇名为#我是技术男,也曾创业过,也拿过风投......#的文章,内容主要是讲述我十年前一次创业失败的血泪史,其目的是为了告诫当下年轻一代的技术小伙伴们“人生苦短,不要创业”。 这篇文章发出之后,我粗略统计了下,算上朋友圈的,估计有超过100+的评论或留言,我把这些内容归纳为三种类型: 一类是激进分子,他们讽刺我,说我满脑袋“鸵鸟思想”,创业失败没啥大不了,人生就是要折腾,哪里跌倒就应该在哪里爬起来,你瞧瞧人家美团的王兴,创业15年多次失败,最终把美团赴港上市身家超400亿,你再瞧瞧人家张某某、李某某…… 二类是保守分子,他们先是安慰我,然后说“创业不是跟风”,对技术出生的人来说,思想单调,视野有限,比起飘无定数的创业,还是在大公司上班稳妥,钱又多,又有保障,别拿自己的身家性命开玩笑,等等…… 三类是信仰分子,不直接评论这段创业经历,上来就说“创业是一种态度”,不是说自己注册个公司,当个说一不二的老板,才是在创业。只要心中有创业精神,自认为不是在为别人打工,这就是创业。 瞧瞧,在我的社交圈里,「无脑创业崇拜」还不在少数,似乎在他们眼里,从不管时机对不

  • CocosCreator基础教程—聊聊scale与size属性(2)

    在CocosCreator引擎编辑中,节点的scale和size属性都可以改变节点内容的大小,如下图中可爱的椰子头,原图尺寸为512*512,在UI编辑时发现太大了,需要·128*128的大小更适合。scale&size此时将节点scale属性设置为0.25好,还是将size属性的高\宽设置128好?回忆一下你在做UI编辑时,习惯用那个属性控制节点大小,思考一下怎样做才是UI开发的最佳实践?1.scale与size的区别scale:节点整体的缩放比例,影响所有子节点。可使用scaleX、scaleY控制节点X\Y轴的缩放。 size:节点内容尺寸,以像素为单位,修改size不影响子节点。size是一个对象,使用width\height控制宽\高像素尺寸。通过上面属性说明,比较容易看出scale与size的区别有两点scale使用比例单位,size使用像素单位scale影响子节点,size不影响子节点在API接口上,scale可以直接使用node.scale访问,但size却不行,需要过node.getContentSize()\node.setContentSize()这两个函

  • 一步步成为linux大神——bash停止解析选项

    一般在bashshell中运行命令时,-a,-v之类的都会被解析为命令的选项,两个减号(doubledash)则可以停止选项(option) 例如运行runuser-ucdhjava-version复制想切换到cdh用户来运行"java-version",此时会报错runuser:invalidoption--'v'复制因为-v被当做了runuser命令的选项 此时应该使用runuser-ucdh--java-version复制这样在解析runuser命令时,就不会尝试解析-v了

  • 机器人:打开潘多拉魔盒

    在百度百家TheBIGTalk上,百度副总裁王海峰、康奈尔机器人实验室主任HodLipson、MIT电脑与人工智能中心主任DanielaRus三位顶级人工智能专家围绕着“机器人重塑未来生活”进行了激烈的观点对撞,给我们带来了不少关于机器人的最新洞见。 一、机器人,已经无处不在市面上最流行的手机操作系统,Android的原意便为机器人,它的LOGO也是一个绿色机器人。事实上,现在大家对机器人的定义都十分广泛,而不是停留在消费者眼中的“长得像人一样的机器人”。只要能够模拟人类的一部分能力,帮助人类完成一些任务的机器,不论是实体的还是虚拟的,都可以纳入机器人范畴。MIT人工智能中心的DanielaRus便给我们介绍了原子机器人。这些机器人就像一个细胞一样,每一个都有自己的一套智力系统,可以在编程之后,与别的原子自动组合组成不同的形状。与HodLipson所主张的3D打印相比是另外一种自下而上的方式。实际上,这也更像是生物本身的生长方式。其外,它还介绍了许多不同的机器人形态,有的可能只是会爬行,有的可能只是一只仿生手臂。原雷锋网主编,现DanielaRus机器人公司COO张海春则认为,机器人的

  • Scrapy的架构一、Scrapy的Twisted引擎模型二、Scrapy的性能模型三、Scrapy架构组件数据流(Data flow)四、Scrapy架构

    Scrapy的架构太重要了,单用一篇文章再总结整合下。前两张图来自《LearningScrapy》,第三张图来自Scrapy1.0中文官方文档(该中文文档只到1.0版),第四张图来自Scrapy1.4英文官方文档(最新版),是我翻译的。一、Scrapy的Twisted引擎模型这里重要的概念是单线程、NIO、延迟项和延迟链。挂衣钩和链子二、Scrapy的性能模型Scrapy包括以下部分:调度器:大量的Request在这里排队,直到下载器处理它们。其中大部分是URL,因此体积不大,也就是说即便有大量请求存在,也可以被下载器及时处理。阻塞器:这是抓取器由后向前进行反馈的一个安全阀,如果进程中的响应大于5MB,阻塞器就会暂停更多的请求进入下载器。这可能会造成性能的波动。下载器:这是对Scrapy的性能最重要的组件。它用复杂的机制限制了并发数。它的延迟(管道长度)等于远程服务器的响应时间,加上网络/操作系统、Python/Twisted的延迟。我们可以调节并发请求数,但是对其它延迟无能为力。下载器的能力受限于CONCURRENT_REQUESTS*设置。爬虫:这是抓取器将Response变为It

  • EasyDSS自定义目录的存储路径写死,该如何更改?

    EasyDSS视频直播点播平台可提供一站式的流媒体服务,能实现视频流媒体的上传、转码、存储、录像、推拉流、直播、点播等功能,支持多屏播放,可兼容Windows、Android、iOS、Mac等操作系统,还能支持CDN转推,具备较强的可拓展性与灵活性。今天和大家分享一个技术干货:EasyDSS自定义目录的存储路径写死,该如何更改?若有用户遇到此类问题,可参照以下步骤进行修改:1)在EasyDSS的服务器获取到easydss.db数据库,如图:2)使用Navicat工具打开easydss.db数据库,如图:3)打开后,找到vod_dirs表:4)将name字段内的路径,改为需要更改的路径:5)更改完成后,那么在EasyDSS内展示和存储的路径,就已经成功更换了,如图:EasyDSS互联网视频云服务可支持H.265/H.264视频播放,随着视频高清技术的发展,EasyDSS也能支持4K视频的直播、点播功能,以及AR、VR等视频能力服务。除此之外,EasyDSS在无人机的场景应用上,用途也非常广泛,通过EasyDSS+RTMP推流技术并融合无人机设备,可应用在城市航拍、地质勘探、环境监测、抢险

  • Aerospike配置

    Aerospike配置

  • lua中删除元素

    lua中删除元素常用办法就是t[k]=nil;table库还提供一个接口:table.remove(); 这两种删除元素的办法有什么区别么? 看了下remove的源码实现,操作就是会把pos后面的元素向前移动;而t[k]=nil不会移动元素,这样会造成表中的元素不连续。 不连续会有什么问题呢? 当你用#操作符对表取最大数量时,遇到nil的项就停止了,算出来的表大小会不准确; 

  • 神经网络学习相关重要链接

    1.深度学习:https://zhuanlan.zhihu.com/p/27857399?refer=YJango 2.神经网络:http://www.cnblogs.com/subconscious/p/5058741.html 3.加州理工学院公开课-机器学习与数据挖掘:http://open.163.com/movie/2012/2/I/D/M8FH262HJ_M8FU27PID.html

  • js添加遮罩层

    直接用代码来说明 <%@PageLanguage="C#"AutoEventWireup="true"CodeBehind="MaskTest.aspx.cs"Inherits="Test07.MaskTest"%> <!DOCTYPEhtml> <htmlxmlns="http://www.w3.org/1999/xhtml"> <headrunat="server"> <metahttp-equiv="Content-Type"content="text/html;charset=utf-8"/> <title></title> </head> <body> <formid="form1"runat="server"> <divid="countdivmaks"style="position:relative"> 在一个层上添加一个遮罩层的实现:<br/> 实现原理:就是在要添加遮罩层的层上里面添加一个层,让该层撑满整个层即可<

  • 项目实训------6-9日计划

    第6日丰富功能页面,将进度条应用于主页面 第7-8日 与前端同学对接,完成前端的最后开发 第9日准备答辩时工作,项目收尾

  • Orabbix监控Oracle 11g

    Orabbix简介说明 orabbix是一个用来监控oracle数据库性能的zabbix插件工具,通过安装在被监控服务器上客户端上收集数据并传给zabbix服务器端,然后通过调用图形显示。具有以下功能: 数据库版本 归档文件 等待的事件(如文件的I/O,单块的读,多块的读,直接读,SQLNet消息,控制文件I/O,日志写等) HitRatio(监控HitRatio的触发,表/存储过程,SQLArea,Body) 逻辑I/O(当前读操作,持续的读操作,块的更改) PGA SGA(固定的缓冲,JAVApool,LargePool,LogBuffer,SharedPool,BufferCache) 物理I/O(重写操作,数据文件写操作,数据文件读操作) SharePool(PoolDictionaryCache,PoolFreeMemory,LibraryCache,SqlArea,Misc.) PinHitRatio(monitorHitRatioonTrigger,Tables/Procedures,SQLArea,Body) Session/Processes(monitorSess

  • 浏览器缓存机制

    浏览器缓存机制,其实主要就是HTTP协议定义的缓存机制(如: Expires; Cache-control等)。但是也有非HTTP协议定义的缓存机制,如使用HTMLMeta 标签,Web开发者可以在HTML页面的<head>节点中加入<meta>标签,代码如下: htmlcode <METAHTTP-EQUIV="Pragma"CONTENT="no-cache"> 上述代码的作用是告诉浏览器当前页面不被缓存,每次访问都需要去服务器拉取。使用上很简单,但只有部分浏览器可以支持,而且所有缓存代理服务器都不支持,因为代理不解析HTML内容本身。 下面我主要介绍HTTP协议定义的缓存机制。 Expires策略 Expires是Web服务器响应消息头字段,在响应http请求时告诉浏览器在过期时间前浏览器可以直接从浏览器缓存取数据,而无需再次请求。  注:Date头域表示消息发送的时间,时间的描述格式由rfc822定义。例如,Date:Mon,31Dec200104:25:57GMT。

  • 装饰器之认证

    auth_status={"username":None,"stat":False} defauth(type): defauth_proc(func): defwrapper(*args,**kwargs): #已经认证通过 ifauth_status["username"]andauth_status["stat"]: ret=func(*args,**kwargs) returnret #未认证文件认证 iftype=="file_auth": print("文件认证") usr=input("请输入用户名:").strip() pwd=input("请输入密码:").strip() usr_info=user_info() forinfoinusr_info: u=eval(info)["username"] p=eval(info)["pwd"] ifusr==uandpwd==str(p): auth_status["username"]=usr auth_status["stat"]=True ret=func(*args,**kwargs) returnret els

  • pycharm最新版注册

    福利啊 下载最新版pycharm专业版,注册服务器填写 http://idea.lanyus.com/就可以直接使用了~~  

相关推荐

推荐阅读