django学习——FBV与CBV

FBV与CBV

FBV

基于函数的视图

CBV

基于类的视图
点击查看代码
# 基本使用
from django.views import View


class MyView(View):
    def get(self,request):
        return HttpResponse('get方法')
    def post(self,request):
        return HttpResponse("post方法")

# CBV路由配置
    path('func4/', views.MyView.as_view()),
"""为什么能够自动根据请求方法的不同执行不同的方法"""
1.突破口
	as_view()
2.CBV与FBV路由匹配本质
	 path('func4/', views.MyView.as_view()),
    # 等价  CBV路由配置本质跟FBV一样
    #  path('func4/', views.view)
    
['get', 'post', 'put', 'patch', 'delete', 'head', 'options', 'trace']
3.源码

 @classonlymethod
    def as_view(cls, **initkwargs):
        """Main entry point for a request-response process."""
        for key in initkwargs:
            if key in cls.http_method_names:
                raise TypeError(
                    'The method name %s is not accepted as a keyword argument '
                    'to %s().' % (key, cls.__name__)
                )
            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))

        def view(request, *args, **kwargs):
            self = cls(**initkwargs)  # self = MyView()  生成一个我们自己写的类的对象
            self.setup(request, *args, **kwargs)  # 给对象赋值属性
            if not hasattr(self, 'request'):
                raise AttributeError(
                    "%s instance has no 'request' attribute. Did you override "
                    "setup() and forget to call super()?" % cls.__name__
                )
            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.
        # 获取当前请求并判断是否属于正常的请求(8个)
        if request.method.lower() in self.http_method_names:
            # 例如: get请求 getattr(自己创建的对象,'get')  handler = 我们自己写的get方法
            handler = getattr(self, request.method.lower(), self.http_method_not_allowed)
        else:
            handler = self.http_method_not_allowed
        return handler(request, *args, **kwargs)  # 执行我们写的get方法并返回该方法的返回值

  • FBV与CBV及源码
      FBV
      	def index(request):
              return HttpResponse('index')
      CBV
      	from django.views import View
      	class MyClassView(View):
              def get(self,request):
                  return HttpResponse('get')
              def post(self,request):
                  return HttpResponse('post')
      	url(r'^login/',views.MyClassView.as_view())
      # 为什么能够根据前期方式的不同自动匹配执行对应的方法
      class View(...):
          @classonlymethod
          def as_view(...):
              def view(...):
                  obj = cls(...)
                  return self.dispatch(...) # 面向对象属性查找顺序
              return view  # FBV与CBV路由其实是一样的
          def dispatch(...):
              if request.method.lower() in [8个方法]:
                  handler = getattr(self.request.method.lower(),'报错')
              else:
                  handler = '报错'
              return handler(...)
posted @ 2022-03-08 14:58  寻月隐君  阅读(37)  评论(0编辑  收藏  举报