• [Django笔记] views.py 深入学习


    views.py 是django MTV 中的主要逻辑层,相当于MVC中的 Controller

    以下的实例都基于这样一个路由表:

    urlpatterns = [
        url(r'^(index)?$', views.index, name='index'),
        url(r'^posts/$', views.PostsView.as_view(), name='posts'),
        url(r'^article/(?P<aid>[0-9]+)/$', views.ArticleView.as_view(), name='detail'),
    ]
    

    view 方法

    虽然views.py是系统自动创建,但是不难发现它并不是必须的。django 关心的是 urls.py 中 import 的是谁。(urls.py 也是项目文件夹下面 urls.py 中引入的)

    from django.shortcuts import render, Http404, HttpResponse
    def index(request):
        # return HttpResponse('Hello world')
        word = request.GET.get('word', '')
        context = {
            'title': 'Dapianzi Carl',
            'word': word if s.strip() else '文档里写的很详细,我只是做一点归纳总结',
        }
        return render(request, 'app/index.html', context)
    

    view 方法返回一个 <HttpResponse Object> ,可以传递给后面的中间件进行处理。django 封装了一些快捷方法比如 render, getObjectOr404等。
    通常只需要使用render。第一个参数是 request 对象,第二个是模板文件,第三个是模板变量。
    个人感觉django 在views中操作models的时候慎用 Models.objects.get() ,动不动就给你来一个 DoesNotExists 惊喜

    快捷函数

    官方文档是最靠谱的Django shortcut functions

    • render 用得最多,上文有粗略介绍。
    • redirect 重载多次,功能看起来挺丰富,笔者实际使用不多。需要配合 Models 的 get_absulute_url 方法
    • get_object_or_404
    • get_list_or_404

    view 类

    不同于view方法, view 类在路由映射中要用 SomeView.as_view()。

    • View 在一个url里根据http method 来处理不同逻辑。处理数据增改操作经常碰到:
        class add(View):
            def get(self, request):
                # view add form
                return render(...)
            def post(self, request):
                # create new item
                return redirect(...)
    
    • TemplateView 一般不需要处理参数的页面可以使用。使用它需要定义template_name属性和重写get_context_data方法
      class Contact(TemplateView):
          template_name = 'app/contact.html'
          def get_context_data(self, **kwargs):
              # 初始化模板变量
              context = super().get_context_data(**kwargs)
              context['email'] = 'carl@dapianzi.me'
              context['interest'] = InterestModel.objects.all()
              return context
      
    • DetailView, ListView 高度封装的 列表view 和 内容view
      ListView 需要重写 get_query_set() 方法,返回的queryset会赋值给key为context_object_name属性的 context
      DetailView 需要指定主键id在 路由表中的名称,然后实现 get_object() 方法
      class PostsView(ListView):
          template_name = 'app/posts.html'
          # 模板中引用的列表变量名称
          context_object_name = 'post_list'
          def get_query_set(self):
              # 注意获取url参数的方法,request对象被封装在 self.request 中
              param = self.request.GET.get('param', '')
              return Articles.objects.filter(name__contains=param)
      
      class ContentView(DetailView):
          # 定义模型
          model = Article
          # 模板
          template_name = 'app/post.html'
          # 模板变量名
          context_object_name = "post"
          # url 路由主键id
          pk_url_kwarg = 'aid'
          def get_object(self, **kwargs):
              obj = super(ArticleView, self).get_object()
              # 对obj进行额外操作,如记录日志,增加浏览数
              obj.views+=1
              obj.save()
              return obj
      

    获取参数

    如果实现的方法带有request参数,那么直接用request.GET/request.POST获取
    实现的方法里没有request参数(比如ListView),通常是类里面的一个属性,这个可能需要查文档看源码。。。

    其他类型的httpresponse

    检查源码或者查看Django文档可以看到有其他类型的Response对象,其实就是文件头不一样而已。下面试导出csv的一个实例:

    def export_csv(self, request, queryset):
        """导出csv"""
        response = StreamingHttpResponse('
    '.join([','.join(
            # list元素转str
            list(map(lambda x: str(x), x))    
        ) 
        for x in list(
            # queryset 转 list
            queryset.values_list('name', 'max_item', 'expire_time', 'active')
        # charset 非常重要
        )]), charset='gbk', content_type='attachment/csv')
        # 额外的http-headers
        response['Content-Disposition'] = 'attachment;filename="test.csv"'
        return response
    
  • 相关阅读:
    当你输入一个网址的时候,实际会发生什么?
    HTTP响应报文与工作原理详解
    DNS系统的解析原理
    spark-streaming集成Kafka处理实时数据
    python分布式环境下的限流器
    使用spark与MySQL进行数据交互的方法
    Linux Redis集群搭建与集群客户端实现
    commons-pool与commons-pool2连接池(Hadoop连接池)
    Kazoo Python Zookeeper 选主
    SpringMVC拦截器Interceptor
  • 原文地址:https://www.cnblogs.com/dapianzi/p/8423383.html
Copyright © 2020-2023  润新知