当前位置: 首页 > news >正文

【Django】REST_Framework框架——视图集ViewSet和ModelViewSet源码解析

在这里插入图片描述


一、ViewSet

继承APIView和ViewSetMixin;
作用也与APIView基本类似,提供了身份认证、权限校验、流量管理等。
ViewSet在开发接口中不经常用

1、ViewSet源码

在ViewSet中,没有提供任何动作action方法,需要我们自己实现action方法。

class ViewSet(ViewSetMixin, views.APIView):
    """
    The base ViewSet class does not provide any actions by default.
    """
    pass

ViewSet视图集类不再限制视图方法名只允许get()、post()等这种情况了,而是实现允许开发者根据自己的需要定义自定义方法名,例如 list() 、create() 等,然后经过路由中使用http和这些视图方法名进行绑定调用

2、ViewSetMixin源码

ViewSet主要通过继承ViewSetMixin来实现在调用as_view()时传入字典{“http请求”:“视图方法”}的映射处理工作,如
{‘get’:’list’,
‘post’:‘create’,
‘put’:‘update’,
‘delete’:‘destory’},

在这里插入图片描述

	@classonlymethod
    def as_view(cls, actions=None, **initkwargs):
        """
        Because of the way class based views create a closure around the
        instantiated view, we need to totally reimplement `.as_view`,
        and slightly modify the view function that is created and returned.
        """
        # The name and description initkwargs may be explicitly overridden for
        # certain route configurations. eg, names of extra actions.
        cls.name = None
        cls.description = None

        # The suffix initkwarg is reserved for displaying the viewset type.
        # This initkwarg should have no effect if the name is provided.
        # eg. 'List' or 'Instance'.
        cls.suffix = None

        # The detail initkwarg is reserved for introspecting the viewset type.
        cls.detail = None

        # Setting a basename allows a view to reverse its action urls. This
        # value is provided by the router through the initkwargs.
        cls.basename = None

        # actions must not be empty
        if not actions:
            raise TypeError("The `actions` argument must be provided when "
                            "calling `.as_view()` on a ViewSet. For example "
                            "`.as_view({'get': 'list'})`")

        # sanitize keyword arguments
        for key in initkwargs:
            if key in cls.http_method_names:
                raise TypeError("You tried to pass in the %s method name as a "
                                "keyword argument to %s(). Don't do that."
                                % (key, cls.__name__))
            if not hasattr(cls, key):
                raise TypeError("%s() received an invalid keyword %r" % (
                    cls.__name__, key))

        # name and suffix are mutually exclusive
        if 'name' in initkwargs and 'suffix' in initkwargs:
            raise TypeError("%s() received both `name` and `suffix`, which are "
                            "mutually exclusive arguments." % (cls.__name__))

        def view(request, *args, **kwargs):
            self = cls(**initkwargs)

            if 'get' in actions and 'head' not in actions:
                actions['head'] = actions['get']

            # We also store the mapping of request methods to actions,
            # so that we can later set the action attribute.
            # eg. `self.action = 'list'` on an incoming GET request.
            self.action_map = actions

            # Bind methods to actions
            # This is the bit that's different to a standard view
            for method, action in actions.items():
                handler = getattr(self, action)
                setattr(self, method, handler)

            self.request = request
            self.args = args
            self.kwargs = kwargs

            # And continue as usual
            return self.dispatch(request, *args, **kwargs)

        # take name and docstring from class
        update_wrapper(view, cls, updated=())

        # and possible attributes set by decorators
        # like csrf_exempt from dispatch
        update_wrapper(view, cls.dispatch, assigned=())

        # We need to set these on the view function, so that breadcrumb
        # generation can pick out these bits of information from a
        # resolved URL.
        view.cls = cls
        view.initkwargs = initkwargs
        view.actions = actions
        return csrf_exempt(view)

二、ModelViewSet

使用ViewSet通常并不方便,因为list、retrieve、create、update、destory等action
方法都需要自己编写,而这些方法与前面讲过的Mixin扩展类提供的方法同名,所以我们可以通过继承Mixin扩展类来复用这些方法而无需自己编写。

ModelViewSet继承自 GenericViewSet,同时包括了ListModelMixin、RetrieveModelMixin、CreateModelMixin、UpdateModelMixin、DestoryModelMixin。

1、ModelViewSet源码

class ModelViewSet(mixins.CreateModelMixin,
                   mixins.RetrieveModelMixin,
                   mixins.UpdateModelMixin,
                   mixins.DestroyModelMixin,
                   mixins.ListModelMixin,
                   GenericViewSet):
    """
    A viewset that provides default `create()`, `retrieve()`, `update()`,
    `partial_update()`, `destroy()` and `list()` actions.
    """
    pass

三、ReadOnlyModelViewSet

ReadOnlyModelViewSet承自 GenericViewSet,同时包括了ListModelMixin、RetrieveModelMixin。

1、ReadOnlyModelViewSet源码

class ReadOnlyModelViewSet(mixins.RetrieveModelMixin,
                           mixins.ListModelMixin,
                           GenericViewSet):
    """
    A viewset that provides default `list()` and `retrieve()` actions.
    """
    pass

四、GenericViewSet

GenericViewSet继承ViewSetMixin、GenericAPIView
继承ViewSetMixin:实现了在调用as_view()时传入字典{“http请求”:“视图方法”}的映射处理工作,如
{‘get’:’list’,
‘post’:‘create’,
‘put’:‘update’,
‘delete’:‘destory’},
继承了GenericAPIView:实现了分页、限流、过滤功能

class GenericViewSet(ViewSetMixin, generics.GenericAPIView):
    """
    The GenericViewSet class does not provide any actions by default,
    but does include the base set of generic view behavior, such as
    the `get_object` and `get_queryset` methods.
    """
    pass

在这里插入图片描述

相关文章:

  • 如何对SAP数据库表进行增删改查操作(3)
  • Spring-06 Xml和注解方式配置Aop
  • 同步请求和异步请求(利用axios)
  • 猿创征文|瑞吉外卖——移动端_笔记
  • SpringBoot异常处理——异常显示的页面
  • 高等数学二从零开始学习的总结笔记(持续更新)
  • 无服务器学习01:基本概念+优点+面临的挑战
  • C#实验二
  • 熟悉c语言结构体
  • uboot源码分析(基于S5PV210)之启动第二阶段
  • 【分布式】分布式系统、Redis中间件 、Cache穿透、击穿、雪崩
  • Rust基础语法
  • 电子知识学习网站
  • 全站最简单 “数据滚动可视化大屏” 【JS基础拿来即用】
  • Vue项目实战——【基于 Vue3.x + Vant UI】实现一个多功能记账本(开发导航栏及公共部分)
  • 【前端学习】-粗谈选择器
  • 3.7、@ResponseBody 和 @RestController
  • Angular4 模板式表单用法以及验证
  • flask接收请求并推入栈
  • Github访问慢解决办法
  • Go 语言编译器的 //go: 详解
  • laravel5.5 视图共享数据
  • Redis的resp协议
  • Service Worker
  • SQL 难点解决:记录的引用
  • 案例分享〡三拾众筹持续交付开发流程支撑创新业务
  • 如何设计一个微型分布式架构?
  • 使用SAX解析XML
  • 腾讯大梁:DevOps最后一棒,有效构建海量运营的持续反馈能力
  • 我的面试准备过程--容器(更新中)
  • 在Mac OS X上安装 Ruby运行环境
  • 正则表达式小结
  • ​ 全球云科技基础设施:亚马逊云科技的海外服务器网络如何演进
  • $(function(){})与(function($){....})(jQuery)的区别
  • (01)ORB-SLAM2源码无死角解析-(56) 闭环线程→计算Sim3:理论推导(1)求解s,t
  • (2)(2.10) LTM telemetry
  • (51单片机)第五章-A/D和D/A工作原理-A/D
  • (MonoGame从入门到放弃-1) MonoGame环境搭建
  • (poj1.2.1)1970(筛选法模拟)
  • (ros//EnvironmentVariables)ros环境变量
  • (附源码)springboot 基于HTML5的个人网页的网站设计与实现 毕业设计 031623
  • (附源码)ssm教师工作量核算统计系统 毕业设计 162307
  • (转)fock函数详解
  • (转载)CentOS查看系统信息|CentOS查看命令
  • *++p:p先自+,然后*p,最终为3 ++*p:先*p,即arr[0]=1,然后再++,最终为2 *p++:值为arr[0],即1,该语句执行完毕后,p指向arr[1]
  • .NET Core Web APi类库如何内嵌运行?
  • .NET WebClient 类下载部分文件会错误?可能是解压缩的锅
  • .NET 将多个程序集合并成单一程序集的 4+3 种方法
  • .NET 跨平台图形库 SkiaSharp 基础应用
  • .NET 中使用 TaskCompletionSource 作为线程同步互斥或异步操作的事件
  • .NET导入Excel数据
  • .Net的C#语言取月份数值对应的MonthName值
  • .Net小白的大学四年,内含面经
  • /etc/fstab 只读无法修改的解决办法
  • @ 代码随想录算法训练营第8周(C语言)|Day53(动态规划)