当前位置: 移动技术网 > IT编程>脚本编程>Python > (django)11类视图

(django)11类视图

2018年10月25日  | 移动技术网IT编程  | 我要评论

超神学院之黑甲,芮城刚,谷俊山与常万全

目录

使用函数方式定义的视图叫函数视图,虽然使用方便,便于理解,但是当一个s视图有多种请求方式的时候,变需要使用分支来编写不同请求方式对应的逻辑。

使用函数视图,代码看上去是这样子的

def my_view(request):
    if request.method == 'get':
        return httpresponse("get")
    if request.method == 'post':
        return httpresponse("post")

1. 使用类视图

基于类的视图的核心是允许你用不同的实例方法来响应不同的http请求方法,而不是在一个视图函数中使用条件分支代码来实现。

创建类视图

使用类视图,代码是这样子的

from django.views import view


class classview(view):

    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

类视图需要继承django提供的 view 类,使用 from django.views import view 导入

注册路由

配置类视图的时候,使用类视图的 as_view 方法注册路由

urlpatterns = [
    url(r'^class_view', views.classview.as_view(), name="class_view")
]

as_view 会返回类中一个方法的引用,它会到 view 中,执行 dispatch 方法, dispatch 会方法会在类中查找类似get\post之类的类方法,然后和请求方式进行匹配,匹配上了,就返回该方法的引用。

如果向上边的类视图发送一个 get 请求,他会把 get 转换为小写形式并和类中的方法进行匹配,然后匹配到 get 方法,会把 get 方法的引用返回到 as_view 调用处。所以在 get 请求下最后 as_viewget 方法的引用。

类视图使用装饰器

可以使用装饰器为类视图增加功能,使用装饰器有三种方式。

  • 在url配置中装饰
  • 在类视图中装饰
  • 使用mixin扩展类

为了便于理解,使用下边的案例做演示

def decorator(func):
    def wrapper(request, *args, **kwargs):
        print('装饰器被调用')
        return func(request, *args, **kwargs)
    return wrapper


class classview(view):

    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

在url中装饰

url(r'^class_view', views.decorator(views.classview.as_view()), name="class_view")

发送 get 或者 post 类型请求打印结果

装饰器被调用

在url中调用该函数,并把 as_view 方法传入即可,这种方式会把所有被请求的函数都进行装饰。

这种方法把装饰放到了url配置中,不利于代码的完整性和可读性,所以一般情况下不使用。

在类视图中装饰

在类视图中使用装饰器不能直接装饰,需要使用 method_decorator 把装饰器转换位适用于类的装饰器。

在我们写的装饰器中,内层函数接收的参数为 request

def decorator(func):
    def wrapper(request, *args, **kwargs):
        print('装饰器被调用')
        return func(request, *args, **kwargs)
    return wrapper

而在类视图的方法中,第一个参数是 self ,所以要使用 method_decorator 把装饰器的第一个参数补充为 self 以使用类视图中的方法。

也可以手动为装饰器添加参数 self

def decorator(func):
    def wrapper(self, request, *args, **kwargs):
        print('装饰器被调用')
        return func(self, request, *args, **kwargs)
    return wrapper

装饰所有方法

可以重写并装饰类的 dispatch 方法,代码如下

class classview(view):

    @method_decorator(decorator)
    def dispatch(self, request, *args, **kwargs):
        return super().dispatch(request, *args, **kwargs)

    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

使用 get 或者 post 方式请求,都会执行装饰器,打印结果

装饰器被调用

只装饰某一个方法

class classview(view):

    @method_decorator(decorator)
    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

只有使用 get 方式请求,才会执行装饰器,打印结果

装饰器被调用

post 方式不会执行装饰器。

method_decorator 的 name 参数

装饰全部方法

@method_decorator(decorator, name="dispatch")
class classview(view):

    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

指定被装饰的方法

@method_decorator(decorator, name="get")
class classview(view):

    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

使用mixin扩展类

扩展类使用了 python 多继承的 mro 特性。

class mymixin(object):
    @classmethod
    def as_view(cls, *args, **kwargs):
        view = super().as_view(*args, **kwargs)
        view = decorator(view)
        return view

class classview(mymixin, view):

    def get(self, request):
        return httpresponse("get")

    def post(self, request):
        return httpresponse("post")

这种方式会装饰所有方法,可以使用这种方式为方法添加多个装饰器。

如对本文有疑问,请在下面进行留言讨论,广大热心网友会与你互动!! 点击进行留言回复

相关文章:

验证码:
移动技术网