详解Django通用视图中的函数包装


Posted in Python onJuly 21, 2015

用函数包装来处理复杂的数据过滤

另一个常见的需求是按URL里的关键字来过滤数据对象。 之前,我们在URLconf中硬编码了出版商的名字,但是如果我们想用一个视图就显示某个任意指定的出版商的所有书籍,那该怎么办呢? 我们可以通过对 object_list 通用视图进行包装来避免 写一大堆的手工代码。 按惯例,我们先从写URL配置开始:

urlpatterns = patterns('',
 (r'^publishers/$', list_detail.object_list, publisher_info),
 **(r'^books/(\w+)/$', books_by_publisher),**
)

接下来,我们写 books_by_publisher 这个视图:

from django.shortcuts import get_object_or_404
from django.views.generic import list_detail
from mysite.books.models import Book, Publisher

def books_by_publisher(request, name):

 # Look up the publisher (and raise a 404 if it can't be found).
 publisher = get_object_or_404(Publisher, name__iexact=name)

 # Use the object_list view for the heavy lifting.
 return list_detail.object_list(
  request,
  queryset = Book.objects.filter(publisher=publisher),
  template_name = 'books/books_by_publisher.html',
  template_object_name = 'book',
  extra_context = {'publisher': publisher}
 )

这样写没问题,因为通用视图就是Python函数。 和其他的视图函数一样,通用视图也是接受一些 参数并返回 HttpResponse 对象。 因此,通过包装通用视图函数可以做更多的事。

注意

注意在前面这个例子中我们在 extra_context中传递了当前出版商这个参数。
处理额外工作

我们再来看看最后一个常用模式:

想象一下我们在 Author 对象里有一个 last_accessed 字段,我们用这个字段来记录最近一次对author的访问。 当然通用视图 object_detail 并不能处理这个问题,但是我们仍然可以很容易地编写一个自定义的视图来更新这个字段。

首先,我们需要在URL配置里设置指向到新的自定义视图:

from mysite.books.views import author_detail

urlpatterns = patterns('',
 # ...
 **(r'^authors/(?P<author_id>\d+)/$', author_detail),**
 # ...
)

接下来写包装函数:

import datetime
from django.shortcuts import get_object_or_404
from django.views.generic import list_detail
from mysite.books.models import Author

def author_detail(request, author_id):
 # Delegate to the generic view and get an HttpResponse.
 response = list_detail.object_detail(
  request,
  queryset = Author.objects.all(),
  object_id = author_id,
 )

 # Record the last accessed date. We do this *after* the call
 # to object_detail(), not before it, so that this won't be called
 # unless the Author actually exists. (If the author doesn't exist,
 # object_detail() will raise Http404, and we won't reach this point.)
 now = datetime.datetime.now()
 Author.objects.filter(id=author_id).update(last_accessed=now)

 return response

注意

除非你添加 last_accessed 字段到你的 Author 模型并创建 books/author_detail.html 模板,否则这段代码不能真正工作。

我们可以用同样的方法修改通用视图的返回值。 如果我们想要提供一个供下载用的 纯文本版本的author列表,我们可以用下面这个视图:

def author_list_plaintext(request):
 response = list_detail.object_list(
  request,
  queryset = Author.objects.all(),
  mimetype = 'text/plain',
  template_name = 'books/author_list.txt'
 )
 response["Content-Disposition"] = "attachment; filename=authors.txt"
 return response

这个方法之所以工作是因为通用视图返回的 HttpResponse 对象可以象一个字典 一样的设置HTTP的头部。 随便说一下,这个 Content-Disposition 的含义是 告诉浏览器下载并保存这个页面,而不是在浏览器中显示它。

Python 相关文章推荐
Python urllib、urllib2、httplib抓取网页代码实例
May 09 Python
python实现域名系统(DNS)正向查询的方法
Apr 19 Python
python中私有函数调用方法解密
Apr 29 Python
PYTHON基础-时间日期处理小结
May 05 Python
python获取代理IP的实例分享
May 07 Python
Jupyter notebook远程访问服务器的方法
May 24 Python
python实现对csv文件的列的内容读取
Jul 04 Python
Python爬虫图片懒加载技术 selenium和PhantomJS解析
Sep 18 Python
python opencv 检测移动物体并截图保存实例
Mar 10 Python
Keras:Unet网络实现多类语义分割方式
Jun 11 Python
如何基于python实现年会抽奖工具
Oct 20 Python
Python Selenium库的基本使用教程
Jan 04 Python
在Python的Django框架中显示对象子集的方法
Jul 21 #Python
在Django的通用视图中处理Context的方法
Jul 21 #Python
Django框架中的对象列表视图使用示例
Jul 21 #Python
在Python的Django框架中使用通用视图的方法
Jul 21 #Python
在Django的模型中执行原始SQL查询的方法
Jul 21 #Python
在Django的模型中添加自定义方法的示例
Jul 21 #Python
详解Python的Django框架中Manager方法的使用
Jul 21 #Python
You might like
超强分页类2.0发布,支持自定义风格,默认4种显示模式
2007/01/02 PHP
修改destoon会员公司的伪静态中的com目录的方法
2014/08/21 PHP
PHP中的魔术方法总结和使用实例
2015/05/11 PHP
分享50个提高PHP执行效率的技巧
2015/12/26 PHP
PHP常用函数总结(180多个)
2016/12/25 PHP
PHP中时间加减函数strtotime用法分析
2017/04/26 PHP
PHP中Notice错误常见解决方法
2017/04/28 PHP
php 策略模式原理与应用深入理解
2019/09/25 PHP
php加速缓存器opcache,apc,xcache,eAccelerator原理与配置方法实例分析
2020/03/02 PHP
jquery.boxy插件的iframe扩展代码
2010/07/02 Javascript
jQuery$命名冲突怎么办如何解决
2014/01/16 Javascript
jQuery+ajax中getJSON() 用法实例
2014/12/22 Javascript
学习javascript的闭包,原型,和匿名函数之旅
2015/10/18 Javascript
CSS+jQuery实现简单的折叠菜单
2016/12/20 Javascript
基于Nodejs利用socket.io实现多人聊天室
2017/02/22 NodeJs
Bootstrap table使用方法记录
2017/08/23 Javascript
使用nodeJs来安装less及编译less文件为css文件的方法
2017/11/20 NodeJs
Node.js在图片模板上生成二维码图片并附带底部文字说明实现详解
2019/08/07 Javascript
JS实现商品橱窗特效
2020/01/09 Javascript
[03:23]我的刀塔你不可能这么可爱 第一期金萌萌的故事
2014/06/20 DOTA
用Python的线程来解决生产者消费问题的示例
2015/04/02 Python
python从入门到精通(DAY 2)
2015/12/20 Python
python执行系统命令后获取返回值的几种方式集合
2018/05/12 Python
Python应用库大全总结
2018/05/30 Python
使用python opencv对目录下图片进行去重的方法
2019/01/12 Python
在Python中合并字典模块ChainMap的隐藏坑【推荐】
2019/06/27 Python
Python3打包exe代码2种方法实例解析
2020/02/17 Python
Python 剪绳子的多种思路实现(动态规划和贪心)
2020/02/24 Python
keras 回调函数Callbacks 断点ModelCheckpoint教程
2020/06/18 Python
使用CSS3设计地图上的雷达定位提示效果
2016/04/05 HTML / CSS
吃透移动端 Html5 响应式布局
2019/12/16 HTML / CSS
英国在线购买马术服装:EQUUS
2019/07/12 全球购物
大学生入党思想汇报
2014/01/14 职场文书
出国留学担保书
2014/05/20 职场文书
电影复兴之路观后感
2015/06/02 职场文书
高一英语教学反思
2016/03/03 职场文书