Django Rest_framework 4(APIView、GenericAPIView、ViewSet)
详解Django DRF框架中APIView、GenericAPIView、ViewSet区别
https://zhuanlan.zhihu.com/p/72527077
View->APIView->GenericAPIView->Mixin扩展类->子类视图
一、DRF类视图-APIView
APIView视图基类:Django框架View类的子类,在View类的基础上封装了一些功能。功能如下:1. 视图request参数变成了Request类的对象,不再是Django原始HttpRequest类的对象;request.data: 保存解析之后的请求体中数据,已经解析为了字典或类字典(QueryDict)。 request.POST|request.body|request.FILESrequest.query_params: 保存解析之后的查询字符串。request.GET2. 响应时可以统一返回Response类的对象,DRF框架会根据客户端请求头的`Accept`将响应数据转换为对应数据格式进行返回,默认返回json,仅支持html或json;`Accept: text/html`:将响应数据转换为html进行返回`Accept: applicaiton/json`:将响应数据转换为json进行返回return Response(响应数据)3. 异常处理:如果视图出现了未处理的异常,DRF框架会对异常进行处理,并将处理的错误响应返回给客户端;4. 认证&权限&限流
二、类视图-GenericAPIView
GenericAPIView视图基类:继承自APIView,在APIView类的基础上封装了一些功能。class 类视图(GenericAPIView):serializer_class = <序列化器类> #指明视图所使用的序列化器类;queryset = <查询集> #指明视图所使用的查询集功能如下:1. 封装了操作序列化器的属性和方法:方法:get_serializer_class:获取视图所使用的序列化器类;eg:如果根据不同的action动作使用不同的额序列化器,需要重写此方法;#视图集对象.action:获取所有执行的操作def get_serializer_class(self):if self.action=="retrieve":return BookDetailSerializerreturn BookSerializerget_serializer:创建一个视图所使用的序列化器类的对象; 从类属性serializer_class中获得serializer的序列化类,提供给Mixin扩展类使用。2. 封装了查询数据库的属性和方法: 方法:get_queryset:获取视图所使用的查询集,群操作就走get_queryset()方法(包括群查,群增等)get_object:从视图所使用的查询集中查询指定的对象(默认根据pk主键进行查询),单操作就走get_object()方法(包括单查,单增等)eg:重写get_queryset#获取当前用户的登录地址def get_queryset(self):return UserAddress.objects.filter(user = self.request.user)eg:重写get_object:#1.获取URL传递过来的参数:id=self.kwargs['pk']定义类视图之后,类视图对象有一个属性kwargs字典,保存从url地址中提取的所有命名参数;#2.取到当前的用户对象:user = self.request.user请求后台时前端header中携带token认证,在后台就可以用request 取到当前的用户对象;def get_object(self):user = self.request.usergoodsid=self.kwargs['pk']userfav = UserFav.objects.filter(user=user, goods_id=goodsid).first()return userfav重写perform_create#将购物车中所有物品结算(删除购物车并将物品移至订单表中)def perform_create(self, serializer):order = serializer.save() # 创建一笔订单global order_snorder_sn += 1order.order_sn = '000000' + str(order_sn)order.save()shopcarts = ShoppingCart.objects.filter(user=self.request.user)for shopcart in shopcarts:orderGoods = OrderGoods()orderGoods.goods_num = shopcart.numsorderGoods.goods = shopcart.goodsorderGoods.order = orderorderGoods.save()# deleteshopcart.delete()3. 过滤&分页pagination_class 分页控制类 filter_backends 过滤控制后端
三、类视图-Mixin扩展类的功能&使用
继承自GenericAPIView之后,使用GenericAPIView中提供的操作序列化器的函数和数据库查询的函数写出的代码变成了通用代码,这些通用代码抽取之后,就是DRF框架提供的5个Mixin扩展类。Mixin扩展类:ListModelMixin(群查):list,封装了获取一组数据通用流程。#除了查询,该list方法会对数据进行过滤和分页CreateModelMixin(单增):create,封装了新增一条数据通用流程。#注意:没有群增的方法,需要自己手动写(******)RetrieveModelMixin(单查):retrieve,封装了获取指定数据通用流程。UpdateModelMixin(更新,修改):update,封装了更新指定数据通用流程。#只有单整体改和单局部改,没有群整体改和群局部改DestroyModelMixin(删除):destroy,封装了删除指定数据通用流程。
视图 | 作用 | 可使用方法 | 父类 |
---|---|---|---|
ListAPIView | 查询多条数据 | get | GenericAPIView ListModelMixin |
CreateAPIView | 新增一条数据 | post | GenericAPIView CreateModelMixin |
RetrieveAPIView | 查询一条数据 | get | GenericAPIView RetrieveModelMixin |
UpdateAPIView | 修改一条数据 | put,patch | GenericAPIView UpdateModelMixin |
DestroyAPIView | 删除一条数据 | delete | GenericAPIView DestroyModelMixin |
RetrieveUpdateAPIView | 单查,更新一条数据 | get,put,patch | GenericAPIView RetrieveModelMixin UpdateModelMixin |
RetrieveUpdateDestroyAPIView | 单查,更新,删除一条数据 | get,put,patch,delete | GenericAPIView RetrieveModelMixin UpdateModelMixin DestroyModelMixin |
ListCreateAPIView | 群查,更新一条 | get,post |
四、视图集-ViewSet视图集的功能&使用
视图集:将操作同一组资源的处理函数放在同一个类中,这个类就是视图集。视图集和类视图的区别?
答:实现同一组接口时,如果使用类视图可能需要多个类视图,而使用视图集时只需要一个视图集。比如:实现图书管理的5个接口时,使用类视图用了2个类视图:BookListVIew和BookDetailView,如果使用视图集只需要一个即可。基本使用:1. 继承自ViewSet(继承自ViewSetMixin和APIView)2. 视图集中的处理函数不再以请求方式(比如:get,post等)命名,而是以对应的action操作命名,常见操作如下:ListModelMixin:获取一组数据createModelMixin:创建一条数据retrieveModelMixin:获取指定数据updateModelMixin:修改指定数据destroyModelMixin:删除指定数据3. 在urls.py进行url地址配置时需要明确指明某种请求方式请求某个地址对应的是视图集中的哪个处理函数。
五、视图集-视图集父类GenericViewSet使用
继承自ViewSetMixin和GenericAPIView,可以配合Mixin扩展类提供对应的处理函数1)工具视图都是GenericAPIView的子类,且不同的子类继承了不同的工具类2)工具视图的功能可以满足需求,只需要继承工具视图,并且提供queryset与serializer_class即可GenericViewSet通常配合Mixin扩展类进行使用。class TestViewSet(ListModelMixin, GenericViewSet):serializer_class=""queryset=""
六、视图集-视图集父类ModelViewSet和ReadOnlyModelViewSet使用
ModelViewSet:继承了5个Mixin扩展类,同时继承了GenericViewSet
ReadOnlyModelViewSet:继承了ListModelMixin, RetireveModelMixin,同时继承了GenericViewSet需求:写一个视图集,提供一下2个API接口:1. 获取所有的图书 GET /books/ -> list2. 获取指定的图书 GET /books/(?P<pk>\d+)/ -> retrieveclass BookInfoViewSet(ReadOnlyModelViewSet):queryset = BookInfo.objects.all()serializer_class = BookInfoSerializer
七、视图集比较
1.常用视图集父类ViewSet继承自APIView和ViewSetMixin,没有提供任何方法,需要自己写GenericViewSet继承GenericAPIView和ViewSetMixin,其中GenericAPIView提供了基础方法,可以直接搭配Mixin扩展类使用,所以我们选这个ModelViewSet 继承GenericViewset,但同时也包括ListModelMixin、CreateModelMixin等mixin扩展类1)视图集都是默认优先继承ViewSetMixin类,再继承一个视图类(GenericAPIView或APIView)
2)ViewSetMixin提供了重写的as_view()方法,继承视图集的视图类,配置路由时调用as_view()必须传入 请求名-函数名 映射关系字典eg: url(r'^v5/books/$', views.BookGenericViewSet.as_view({'get': 'my_get_list'})),表示get请求会交给my_get_list视图函数处理
八、路由Router
作用:动态生成视图集中处理函数的url配置项。使用:
1. 创建Router类的对象#DefaultRouter会多附带一个默认的API根视图,返回一个包含所有列表视图的超链接响应数据。router = SimpleRouter()router = DefaultRouter()
2. 注册视图集router.register(<prefix>, <viewset>, <base_name>)例如:router.register('books', views.BookInfoViewSet, base_name='books')
3. 将动态生成的配置项列表添加到urlpatterns中方法一:urlpatterns += router.urls方法二:urlpatterns = [path(r'^', include(router.urls)),]方法三:urlpatterns.extend(router.urls)
九、常见问题
1.GenericAPIView与APIView两大继承视图的区别
1)GenericViewSet和ViewSet都继承了ViewSetMixin,as_view都可以配置 请求-函数 映射
2)GenericViewSet继承的是GenericAPIView视图类,用来完成标准的 model 类操作接口
3)ViewSet继承的是APIView视图类,用来完成不需要 model 类参与,或是非标准的 model 类操作接口post请求在标准的 model 类操作下就是新增接口,登陆的post不满足post请求验证码的接口,不需要 model 类的参与
案例:登陆的post请求,并不是完成数据的新增,只是用post提交数据,得到的结果也不是登陆的用户信息,而是登陆的认证信息
2.类视图和视图集区别?
答:实现同一组接口时,如果使用类视图可能需要多个类视图,而使用视图集时只需要一个视图集。比如:实现图书管理的5个接口时,使用类视图用了2个类视图:BookListVIew和BookDetailView,如果使用视图集只需要一个即可。
Django Rest_framework 4(APIView、GenericAPIView、ViewSet)相关推荐
- Django Rest_Framework(DRF)
文章目录 一.主要内容 1.web开发模式 2.API接口 3.接口测试工具:Postman 4.序列化 5.Restful规范(重点) 6.Django Rest_Framework(drf) 7. ...
- DRF之View、APIView以及GenericAPIView
一.APIView[基本视图类] 序列化后前端展示都是json数据,反序列化(post.put)也以json数据格式输入,这种用法存在很大的局限性,如果前端想以application/x-www-fo ...
- django_rest_framework之GenericAPIView(二)之搜索、排序、分页讲解
一.搜索过滤的步骤 1.在全局配置文件settings.py中设置'DEFAULT_FILTER_BACKENDS','DEFAULT_FILTER_BACKENDS'指定使用的过滤搜索引擎类路径(S ...
- Django 基础(12)-Django drf 分页查询(批量查询)、自定义分页器
文章目录 Django drf 分页查询(批量查询) PageNumberPagination:普通分页 Django 自定义分页器 自定义批量查询的返回结构 LimitOffsetPaginatio ...
- Django实现登录、注册、修改密码、重置密码
需求: 1.实现Django的登录 2.实现Django的注册,校验用户名.密码的长度为6-20,邮箱是否合法,序列化等 3.实现根据ID或者用户名修改密码,ID为数据库的用户表的id 4.实现重置密 ...
- Django框架项目之课程主页——课程页页面、课程表分析、课程表数据、课程页面、课程接口、前台、后台
文章目录 1-课程页页面 课程组件 2 课程主页之课程表分析 课程表分析 免费课案例 创建models:course/models.py 注册models:course/adminx.py 数据库迁移 ...
- 面经 - OpenStack(Docker、Django、K8S、SDN)知识点
文章目录 概述 OpenStack 虚拟化 kvm 网络虚拟化 基本技术 Memcached Etcd 消息队列 概念 交换机类型 缺点 重复投递问题 顺序投递问题 restful api Horiz ...
- Linux安装Nginx、Redis、django
部署Nginx 部署Redis 安装Redis redis事物 服务器管理命令 慢查询日志 主从复制 Redis-Sentinel cluser分片集群 安装python 操作redis数据 部署Dj ...
- Django框架(十)--常用字段、参数、元信息、多对多关联关系
一.ORM字段 # AutoField() int自增列,必须填入参数 primary_key=True.当model中如果没有自增列,则自动会创建一个列名为id的列# IntegerField() ...
最新文章
- mysql union 优化_mysql 5.7.3 对union all 的优化
- java的内部类和匿名类剖析
- 华东交通大学计算机调剂,华东交通大学2018考研调剂信息
- WIFI-MESH + 蓝牙MESH在智能家居领域有着广泛的应用场景,他们的区别到底在哪里呢
- VTK:Utilities之RenderScalarToFloatBuffer
- 「SDOI2016」储能表(数位dp)
- Docker系列(一):容器监控工具Weave Scope安装
- 回答一位朋友关于 SAP SRM 行业 转 CRM 行业的咨询
- 21个ui设计技巧,让你的设计不落伍
- srt编辑的文件在linux显示乱码,解决看本地视频srt字幕乱码问题教程-srt文件
- angular2之pdf文件操作大全
- java arraylist 添加对象_如何在Java中将对象添加到ArrayList
- mergesort unrecursive 归并排序的非递归实现
- 51nod-独木舟问题
- 距离感应器黑屏,如何一直亮屏
- 【YOLO3D】:端到端3D点云输入的实时检测
- MySQL 实时同步 解决方案
- 2012年8月编程语言就业趋势
- MySQL之按日期查询表数据
- python 数据分析 电信_基于Python的电信客户流失分析和预测