Python Web开发模板引擎优缺点总结
发布时间:2023-08-02 22:36:29
做 Web 开发少不了要与模板引擎打交道。我陆续也接触了 Python 的不少模板引擎,感觉可以总结一下了。
一、首先按照我的熟悉程度列一下:
pyTenjin:我在开发 Doodle 和 91 外教时使用。
Tornado.template:我在开发知乎日报时使用。
PyJade:我在开发知乎日报时接触过。
Mako:我只在一个早期就夭折了的小项目里用过。
Jinja2:我只拿它做过一些 demo。
其他就不提了,例如 Django 的模板,据说又慢又难用,我根本就没接触过。
二、再说性能
很多测试就是弄个大循环什么的,很没技术含量。其实模板的渲染时间主要消耗在字符串处理上,包括拼接、编码、转义等,而循环测的则是 Python runtime 的性能。
所以我还是用实际的例子来测试吧,最终选择了 Doodle 的首页。它有几个子模板、几个循环、几个函数调用和很多个变量,具有一定代表性。考虑到 pyTenjin 以外的模板引擎不支持局部缓存,我就把用到缓存的侧边栏去掉了,只渲染主体部分。
渲染 1000 次的结果为:pyTenjin 耗时 0.65 秒,取消预处理后耗时 0.9 秒;Tornado.template 耗时 1.0 秒;Jinja2 耗时 1.1 秒。
测试代码有几百行,19 个文件,我就懒得列出来了。其他模板引擎也懒得测了。
@pyTenjin 的优势很明显,特别是它支持预处理。这个预处理的主要作用是把一些常量先编译好,渲染时就不用再处理了(因为已经变成字符串了);此外,有些功能可以静态地决定是否开启,而预处理可以把那些不需要的功能代码(主要是 if 分支)提前去掉。此外还能缓存任意代码段的渲染结果,在一段时间内无需重新渲染。
@Jinja2 比 Tornado.template 慢是我没想到的,好像与很多测试不符。
@Mako 预计和 Jinja2 差不多。它也能缓存代码段的渲染结果。
@PyJade 需要把 Jade 模板转成其他模板,且无缓存,预计会慢很多。
考虑到除 PyJade 外肯定不存在几倍的性能差距,所以挑个好用的即可。
三、最后说易用性
@pyTenjin 的优点是可以写任意 Python 代码。
缺点是标记比较复杂和独特,有 <?py ... ?>、<?PY ... ?>、#{...}、#{{...}}、{==...==}、{#==...==#}、${...}、${{...}}、{#=...=#} 和 {#==...==#} 这么多种,不过看上去还挺萌的。
由于使用了 < 和 > 符号,在 HTML 标签内部使用时,会阻碍编辑器进行语法解析。
另外,它的 tagattr() 方法在 expr 参数为 0 时当成了 True 来处理,需要改源码来修正,而它又没有开源项目可以提交 pull request。
而且它只有一个开发者,已经有一年多没更新了,活跃度明显不够。
@Tornado.template 的优点是与 Tornado 搭配还不错(毕竟是自带的),功能和性能都还行。
缺点是出错时很难定位到是哪写错了,而且与其他模板引擎相比,功能确实少了点(不过我还没遇到不够用的情况)。
另外,{% raw ... %} 写起来好麻烦。None 在输出时会显示成 None,而不是空字符串,导致写起来很累。
它输出的 HTML 代码是去掉头尾空格的,不过单独的 Python 代码行会显示成空行,看上去比较怪。
@Jinja2 的优点是功能多,定义了很多辅助函数,有 filter,也有内联的 if 表达式这种语法糖,写起来比较舒服。此外,它能够调整空白,这使得它输出的 HTML 比较好看。
缺点是学习成本较高,语法也不是纯 Python 了,甚至不能 import Python 模块和使用 [item for item in list if item] 这种列表解析表达式。
另一个严重的缺点是不能输出非 ASCII 的字符串, 遇到这种情况必须使用 unicode 类型,但要保证这点很麻烦。
@Mako 的优点是和 pyTenjin 一样可以写任意 Python 代码,又和 Jinja2 一样支持 filter(其实习惯了函数调用的话)。
缺点也是学习成本较高,语法比较复杂,对 HTML 编辑器不友好。
@PyJade 的优点是写起来最快(特别是对前端而言),没什么多余的东西。
缺点和 Jinja2 一样,更惨的是它几乎没有文档,而且最新的 release 版不可用,需要用开发版。
目前看来,我还是继续用 pyTenjin 算了,其他的要么不好用,要么学习成本比较高,而且多出来的功能感觉并不是非有不可的。


猜你喜欢
- 具体代码如下所示:import tkinter as tkimport tkinter.messageboximport copyimpor
- 前言一般从数据库或者是从日志文件读出的数据均带有时间序列,做时序数据处理或者实时分析都需要对其时间序列进行归类归档。而Pandas是处理这些
- sql中的 IF 条件语句的用法IF 表达式IF( expr1 , expr2 , expr3 )expr1 的值为 TRUE,则返回值为
- 处理办法,删除该文件,或清空该文件内容;我的处理是清空后,再设置该文件权限为Everyone拒绝访问。
- 本文实例为大家分享了python matplotlib实现条形图填充效果的具体代码,供大家参考,具体内容如下写专利用的python里面的ma
- 本文实例讲述了Python基于回溯法子集树模板实现图的遍历功能。分享给大家供大家参考,具体如下:问题一个图:A --> BA --&g
- 很多人都听过WAMP这个词吧,首先来看WAMP是什么意思?Windows下的Apache+MySQL+PHP,称为WAMP。属于WAMP环境
- 在MySQL 8.0.16版本中安装可能会出现部分错误提示已经不使用“UTF8B3”而是使用了“UTF8B4”#//////////////
- 使用pandas处理向量化的数据,进行数据的替换时不仅仅能够进行字符串的替换也能够处理数字。做简单的示例如下:In [4]: data =
- Oracle数据文件默认大小上限是32G,如果要数据文件大于32G,需要在数据库创建之初就设置好。表空间数据文件容量与DB_BLOCK_SI
- python通过安装使用paramiko模块,将本地文件上传到服务器上import paramikoimport datetimeimpor
- 列表的创建创建列表,Python底层只提供了唯一一个Python/C API,也就是PyList_New。这个函数接收一个size参数,允许
- deque 是 double-ended queue的缩写,类似于 list,不过提供了在两端插入和删除的操作。appendleft 在列表
- 最近在重构公司以前产品的前端代码,摈弃了以前的session-cookie鉴权方式,采用token鉴权,忙里偷闲觉得有必要对几种常见的鉴权方
- 在安装mha4mysql时,大概步骤是:解压,perl Makefile.PL,make, make install。在执行 perl Ma
- 验证码制作#string模块自带数字、字母、特殊字符变量集合,不需要我们手写集合import stringimport randomimpo
- 本文为大家分享了路由嵌套的SPA实现的步骤:A(/a)组件需要嵌套B组件(/b)和C组件(/c)①准备嵌套其它组价的父组件 指定一个容器在A
- 直接上代码:# -*- coding: utf-8 -*- import Queue import threadingimport urll
- 有如下格式的文本文件/“/请/!/”/“/请/!/”/两名/剑士/各自/倒转/剑尖/,/右手/握/剑柄/,/左手/搭于/右手/手背/,/躬身
- 格式化字符串由占位符和普通字符组合而成。占位符由'%'打头,动词结尾。占位符由五类元素组成: 标志位(flag),宽度,精度