防止jinja2自动转义,以将数据库中的html片段插入到所在html中(以html输出,而非HTML代码输出)

本文转载自http://tieba.baidu.com/p/4074015134,感谢原作者!

首先,Jinja2是一个模板引擎。如果连模板引擎是什么都不知道的话就请不要看了。本文仅供需要的人研究(以及闲的要命的人)。。

摘要:Jinjia默认自动转义HTML,safe过滤器可以取消这个功能

Jinja2(下面用jinjia代替)是Flask的默认模板引擎,在普通HTML基础上增加了一堆函数和功能方便后端和前端交换数据(比方说怎样将数据库的内容扔进HTML?每次都生成一个新的HTML文件?有了Jinjia,一切都方便多了~)

现在,我使用我的comment网站做例子。这是我的网站,功能是大家可以添加任意的comment。文本会存储在一个sqlite3的数据库,然后会在主页展示:
这里写图片描述

现在,让我们来模拟添加一个comment。这个comment使用了<strong>HTML标签,我们来看看效果。像这样:
这里写图片描述

看,我们的文字并没有被加粗!这是为什么呢?我们可以从Flask文档中的一部分得到解答:

模板继承让模板用起来相当顺手。如欲了解继承的工作机理,请跳转到 模板继承 模式的文档。最起码,模板继承能使特定元素 (比如页眉、导航栏和页脚)可以出现在所有的页面。

自动转义功能默认是开启的,所以如果 name 包含 HTML ,它将会被自动转义。如果你能信任一个变量,并且你知道它是安全的(例如一个模块把 Wiki 标记转换为 HTML),你可以用 Markup 类或 |safe 过滤器在模板中把它标记为安全的。在 Jinja 2 文档中,你会看到更多的例子。

这里写图片描述

因此,根据文档我们可以得知,如果想让HTML不会被转义,我们需要启用safe过滤器。现在让我们回到网页源码,来研究下究竟是怎么回事:

这里写图片描述

我们可以看到文本被直接的显示出来了。包含在双大括号内的文本意味着变量,这些变量就是数据库内的文本。我们不需要关心这些,现在让我们对body使用safe过滤器:

这里写图片描述

成功!现在我们在body的标签被应用了,文本呈现出了粗体。然而因为我们没有对title启用safe过滤器,所以title并没有被加粗。

这里写图片描述

safe意味着禁用全部转义。这同时意味着我们可以使用全部的HTML标签。在一个博客等网站启用safe过滤器可以让博客更加绚丽多彩:

这里写图片描述

这里写图片描述

好了,本次科普就到这里。虽然启用safe过滤器可以让文章更加绚丽多彩,但是如果用户不被信任的话将是特别危险的,请记住:“永远不要相信用户的输入”,另外还包括用户的HTTP Header、Cookie、用户名、验证码、密码、标点符号、空格、空行、表情、时间和日期……

有关怎样启用部分HTML标签、验证用户的输入是否危险等,请参阅Flask和Jinjia2文档。
本文章遵守CC-BY-NC-ND协议。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章