django 类通用视图详解

view() :

    该类为所有类视图的父类,处于最底层,仅仅只对请求参数做校验后,给特定请求方法做特定调用。

用法:

url中定位到类方法:Aa.as_view() ——> View.as_view()方法对请求参数做判断后,转到View.dispatch() ——> 找到Aa.get() 或者Aa.post() 或者Aa.其他请求方法 ———>处理完成后返回view()

    需要对请求方式做特定处理,可以自行修改dispatch()方法。

 

源码:

class View(object):
    """
    Intentionally simple parent class for all views. Only implements
    dispatch-by-method and simple sanity checking.
      该视图为所有类视图的父类,处于最底层,仅仅只实现了给特定的请求方式
      进行特定方法的调度
    """
      # http 所有请求方式的列表
    http_method_names = [‘get‘, ‘post‘, ‘put‘, ‘patch‘, ‘delete‘, ‘head‘, ‘options‘, ‘trace‘]
    def __init__(self, **kwargs):
        """
        Constructor. Called in the URLconf; can contain helpful extra
        keyword arguments, and other things.
            # 构造函数接收键值对参数,该参数来源于 URLconf配置中的传递
        """
        # Go through keyword arguments, and either save their values to our
        # instance, or raise an error.
            # 接收关键字参数,并将其添加到实例中或者引发错误
        for key, value in six.iteritems(kwargs):
            setattr(self, key, value)
    @classonlymethod
    def as_view(cls, **initkwargs):
        """
            # as_view 是一个闭包,做了一些校验工作后,再返回view函数
        Main entry point for a request-response process.
        """
        for key in initkwargs:
                  #as_view()方法中,如果传递的关键字参数key为默认的http 请求方法,则报错,
                  #默认不允许使用http请求方法作为参数
            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__))
                  # as_view()方法中,如果传递过来的参数key 不在as_view()的属性中,也报错
            if not hasattr(cls, key):
                raise TypeError("%s() received an invalid keyword %r. as_view "
                                "only accepts arguments that are already "
                                "attributes of the class." % (cls.__name__, key))
            # view 方法作用是给请求对象添加三个参数,调用dispatch方法处理请求
        def view(request, *args, **kwargs): # 作用:增加属性,调用dispatch方法
            self = cls(**initkwargs) # 调用as_view 父类,创建一个实例对象
                  # 如果对象中有get属性,或者没有head属性,就创建head属性
            if hasattr(self, ‘get‘) and not hasattr(self, ‘head‘):
                self.head = self.get
                  # 为对象创建request、args和kwargs 三个属性
            self.request = request
            self.args = args
            self.kwargs = kwargs
                  #调用dispatch 函数找到指定的请求方法,
            return self.dispatch(request, *args, **kwargs)
        view.view_class = cls
        view.view_initkwargs = initkwargs
        # 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=())
        return view
      # 找到请求的方法,执行该方法
    def dispatch(self, request, *args, **kwargs):
        # Try to dispatch to the right method; if a method doesn‘t exist,
        # defer to the error handler. Also defer to the error handler if the
        # request method isn‘t on the approved list.
            # 找到请求的方法,如果请求方法不在允许的列表中或者请求方法不存在就按照错误处理
            # http_method_names = [‘get‘, ‘post‘, ‘put‘, ‘patch‘, ‘delete‘, ‘head‘, ‘options‘, ‘trace‘]
            # 如果请求方法存在,则取出该方法
        if request.method.lower() in self.http_method_names:
            handler = getattr(self, request.method.lower(), self.http_method_not_allowed)
            # 如果不存在则报405错误
        else:
            handler = self.http_method_not_allowed
            # 执行该请求方法
        return handler(request, *args, **kwargs)
    def http_method_not_allowed(self, request, *args, **kwargs):
        logger.warning(
            ‘Method Not Allowed (%s): %s‘, request.method, request.path,
            extra={‘status_code‘: 405, ‘request‘: request}
        )
        return http.HttpResponseNotAllowed(self._allowed_methods())
    def options(self, request, *args, **kwargs):
        """
        Handles responding to requests for the OPTIONS HTTP verb.
        """
        response = http.HttpResponse()
        response[‘Allow‘] = ‘, ‘.join(self._allowed_methods())
        response[‘Content-Length‘] = ‘0‘
        return response
    def _allowed_methods(self):
        return [m.upper() for m in self.http_method_names if hasattr(self, m)]

   用法实例:

class LoginUserView(View):
   def dispatch(self, request, *args, **kwargs):
      print "进入了改写后的dispatch方法"
      discontext = super(LoginUserView, self).dispatch(request, *args, **kwargs)
      print "没有改变调用请求方式,直接返回原始dispatch调用"
      return discontext
   def post(self, request):
      context = userservice.login_user(request=request)
      return JsonResponse(context)

  

ListView() :

    

原文地址:https://www.cnblogs.com/cpy-devops/p/10368382.html

时间: 2024-08-28 03:24:25

django 类通用视图详解的相关文章

学习ASP .NET MVC5官方教程总结(七)Edit方法和Edit视图详解

学习ASP .NET MVC5官方教程总结(七)Edit方法和Edit视图详解 在本章中,我们研究生成的Edit方法和视图.但在研究之前,我们先将 release date 弄得好看一点.打开Models\Movie.cs 文件.先添加一个引用: <span style="font-size:14px;">using System.ComponentModel.DataAnnotations;</span> 然后在Movie类中添加以下代码: [Display(

创建物化视图详解(图解)

创建物化视图详解 一,什么是物化视图 物化视图是包括一个查询结果的数据库对象,它是远程数据的的本地副本,或者用来生成基于数据表求和的汇总表.物化视图存储基于远程表的数据,也可以称为快照. 二,作用. 在类似统计功能中,查询操作是无可避免,而这些查询操作如果很频繁,对整体数据库性能是很致命的.而物化视图实现远程数据源与本地数据的实时同步,也就是定时刷新,通过在本地创建物化视图可以大大提高查询效率. 三,流程图: 当用户要跨本地数据库,访问另外一个数据库表中的数据时,本地数据库中必须创建了远程数据库

【转】UML类图与类的关系详解

UML类图与类的关系详解   2011-04-21 来源:网络   在画类图的时候,理清类和类之间的关系是重点.类的关系有泛化(Generalization).实现(Realization).依赖(Dependency)和关联(Association).其中关联又分为一般关联关系和聚合关系(Aggregation),合成关系(Composition).下面我们结合实例理解这些关系. 基本概念 类图(Class Diagram): 类图是面向对象系统建模中最常用和最重要的图,是定义其它图的基础.类

Android Environment类的接口详解

Android应用开发中,常使用Environment类去获取外部存储目录,在访问外部存储之前一定要先判断外部存储是否已经是可使用(已挂载&可使用)状态, 并且需要在AndroidManifest.xml文件中添加外部存储读和写的权限. Environment类中提供了几个静态常量用于标识外部存储的状态,这些状态都是String类型 MEDIA_BAD_REMOVAL 在没有挂载前存储媒体已经被移除. MEDIA_CHECKING 正在检查存储媒体. MEDIA_MOUNTED 存储媒体已经挂载

ORACLE物化视图详解

一.物化的一般用法物化视图是一种特殊的物理表,"物化"(Materialized)视图是相对普通视图而言的.普通视图是虚拟表,应用的局限性大,任何对视图的查询,oracle都实际上转换为视图SQL语句的查询.这样对整体查询性能的提高,并没有实质上的好处. 1.物化视图的类型ON DEMAND.ON COMMIT.二者的区别在于刷新方法的不同,ON DEMAND顾名思义,仅在该物化视图"需要"被刷新了,才进行刷新(REFRESH),即更新物化视图,以保证和基表数据的一

07--c++类的构造函数详解

c++类的构造函数详解 c++构造函数的知识在各种c++教材上已有介绍,不过初学者往往不太注意观察和总结其中各种构造函数的特点和用法,故在此我根据自己的c++编程经验总结了一下c++中各种构造函数的特点,并附上例子,希望对初学者有所帮助. c++类的构造函数详解 一. 构造函数是干什么的 class Counter{ public:         // 类Counter的构造函数         // 特点:以类名作为函数名,无返回类型         Counter()         { 

[转]c++类的构造函数详解

c++构造函数的知识在各种c++教材上已有介绍,不过初学者往往不太注意观察和总结其中各种构造函数的特点和用法,故在此我根据自己的c++编程经验总结了一下c++中各种构造函数的特点,并附上例子,希望对初学者有所帮助. c++类的构造函数详解 一. 构造函数是干什么的 class Counter{ public:         // 类Counter的构造函数         // 特点:以类名作为函数名,无返回类型         Counter()         {             

UML类图与类的关系详解--转

http://www.uml.org.cn/oobject/201104212.asp 原文地址 UML类图与类的关系详解   2011-04-21 来源:网络   在画类图的时候,理清类和类之间的关系是重点.类的关系有泛化(Generalization).实现(Realization).依赖(Dependency)和关联(Association).其中关联又分为一般关联关系和聚合关系(Aggregation),合成关系(Composition).下面我们结合实例理解这些关系. 基本概念 类图(

phpcms加载系统类与加载应用类之区别详解

<?php 1. 加载系统类方法load_sys_class($classname, $path = ''", $initialize = 1)系统类文件所在的文件路径:/phpcms/libs/classes/文件夹下参数说明:@param string $classname 类名@param string $path 扩展地址@param intger $initialize 是否初始化 例子:如要调用系统Form类的生成验证码函数:checkcode() ,看下面例子pc_base: