前面也提到过在Flask中最核心的两个组件是Werkzeug和Jinja2模板。其中Werkzeug在前一节已经详细说明了。现在这一节主要是来谈谈Jinja2模板。

一、为什么需要引入模板:

  在进行软件开发的时候,我们都希望开发的软件能够有很低的耦合度。而在视图中主要是处理业务逻辑和返回响应的,在web开发中,响应主要是渲染HTML文本,如果把渲染的这一个过程在视图中做的话,会导致耦合度特别高,难以维护。这样就引入了模板,目的是为了把视图中的业务处理和响应分开,这样维护的成本就会降低。

二、Jinja2模板引擎

  1. 什么是模板?

    模板其实是一个包含响应的文件,只不过其中使用了很多变量来作为占位符,这些变量的值是通过视图传入的。

  Jinja2是一个模板引擎,使用Python实现的。起源于Django中的模板,然后又扩充了一些额外的功能。

  在Flask中使用render_template来使用某个模板文件,模板中的变量通过字典的方式传入。

  2. 语法规则:

    {{ 变量 }}:直接在浏览器中输出变量值

    {% if 条件%}.....{%elif 条件 %}.......{% endif %}:用来控制输入

    {%for item in 序列 %} {% endfor %}:表示一个循环,其内部有一些特殊的变量:

      loop.index:表示下标从1开始,

      loop.index0:表示下标从0开始,

      loop.length:表示序列中元素的个数

  3.过滤器:

    过滤器的本质就是一个函数,但是不能定义在模板中,而是定义在.py文件中。

    作用:对输出的变量做一些处理,如格式化。

    使用方式:{{ 变量 | 过滤器1  | 过滤器2 | 过滤器3 | ....}}

    常用内置过滤器: upper、lower、capitalize、safe等。

    重点说一下safe过滤器。从字面意思看,也知道这个过滤器是起到安全的作用。因为Jinja2模板默认是开启转义的。也就是说一些特殊的字符在渲染的时候,会屏蔽其特殊功能,这样输出的字符串浏览器就会把它当做是一般的字符串,不会对它进行翻译,这样通过JS也无法修改其样式或其内容了。使用safe的话,一些特殊的字符就有特殊的作用,浏览器就会将其翻译过来!比如当视图往模板中传入"<h1>Index</h1>",如果没有使用safe过滤器的话,展示在浏览器的效果就是"<h1>index</h1>";但如果使用了safe过滤器的话,展示的结果就是变成一级标题!

    

    自定义过滤器:除了使用Flask内置的过滤器外,我们还可以自定义一些过滤器。

 # 自定义过滤器
 def my_filter(name):
     return name.upper()

 # 把过滤器添加到系统的过滤器中
 app.add_template_filter(my_filter, 'myfilter1')

 # 过滤器实现形式二,使用装饰器
 @app.template_filter('myfilter2')
 def my_filter2(str):
     return str.capitalize()

四、模板代码复用

  1. 为什么需要模板代码复用?

   一个网页一般是有头部、中间体和尾部三个部分。同一个网站中可能有很多个页面,但是头部和尾部页面的重合度特别高,这部分的代码我们可以通过其他方式给获取过来,而不是再继续写。这样我们只需要实现中间部分的网页就可以了。这里电商网页为例。

  

   

  2. 代码复用的方式:

  (1). 继承:{ % block xxx%} { % endblock xxx%}

    在子模板中使用{% extends 'base.html' %} 把父模板中的数据继承过来,这条语句一般写在子模板中的第一行;

    使用这种方式就相当于在父模板中,挖很多坑,然后在子模板中通过使用{% block content %}{% endblock content%}来重写中间体的内容,实现自定义功能;

    除了把父模板中的某段数据给改写了之外,还可以使用{{ super() }}来调用父模板中某段数据。

  (2). 宏: {% macro fun_name(arg1, arg2,....) %} 某个功能 {% endmacro %}

    宏的本质上是一个函数,定义在模板当中。

    使用函数的目的也是为了把反复编写的模板代码封装起来,如果其他地方需要用到的话,可以直接想调用函数的方式进行获取

    如果有多处用到重复的模板代码,那么可以单独创建一个HTML文件,用来存放宏。然后在需要用到的地方包含这个文件。

      {%  import 'macro.html' as functions %}

      {{ functions.func() }}

  (3). 包含:{% include 'hello.html' %}

    包含相当于把被包含的文件(hello.html)重新复制了一份到当前文件,然后再返回给浏览器。

    如果被包含的文件不存在,那么会发生TemplateNotFound错误。通过添加 ignore missing关键字来忽略这个错误。

    

  (4). 小结:

    继承、宏、包含都可以实现代码复用的功能,其中继承相对来说用的比较广泛一些!

    继承的本质是对父模板中的某段代码进行重写,一般用来实现多个页面中重复不变的区域,如顶部和底部。

    宏就相当于函数,可以传入参数,定义,然后再进行调用

    包含是直接将目标模板文件整个渲染出来,相当于复制了一份。

三、CSRF

  1. 什么是CSRF?

   CSRF的全称是:跨站请求伪造(Cross Site Request Forgery)。是指攻击者获取了用户的一些私人信息,然后去攻击信任用户的网站!

  2. 攻击原理图:

   

  3. 如何采取安全措施呢?

   比较csrf_token,即当用户请求时服务器端设置一个csrf_token给客户端,保存在浏览器中;同时当用户执行form表单提交操作时,需要把csrf_token一起和其他参数给提交上来,但是这个参数不是用户自己输入的,而是服务器端把它隐藏在表单中。在服务器端把来自请求中cookie里的csrf_token和post请求中携带的csrf_token参数进行对比,如果不相等,那么就不能继续往下执行。如果成功的话,说明有可能是安全访问!为什么是有可能呢?因为可能你设置csrf_token的原理被别人截取到了,那么也就无效了!所以这个设置只能针对一般的,对技术不是太好的人有效。

   这也就是为什么Flask-WTF扩展包中,如果需要使用里面的form表单,必须要设置一个csrf_token, 然后在配置文件中设置SECRET_KEY。

  

Python框架学习之Flask中的Jinja2模板的更多相关文章

  1. Python框架学习之Flask中的视图及路由

    在前面一讲中我们学习如何创建一个简单的Flask项目,并做了一些简单的分析.接下来在这一节中就主要来讲讲Flask中最核心的内容之一:Werkzeug工具箱.Werkzeug是一个遵循WSGI协议的P ...

  2. Python框架学习之Flask中的常用扩展包

    Flask框架是一个扩展性非常强的框架,所以导致它有非常多的扩展包.这些扩展包的功能都很强大.本节主要汇总一些常用的扩展包. 一. Flask-Script pip install flask-scr ...

  3. Python框架学习之Flask中的蓝图与单元测试

    因为Flask框架的集成度很低,随着Flask项目文件的增多,会导致不太好管理.但如果对一个项目进行模块化管理的,那样子管理起来就会特别方便.而在Flask中刚好就提供了这么一个特别好用的工具蓝图(B ...

  4. Python框架学习之Flask中的数据库操作

    数据库操作在web开发中扮演着一个很重要的角色,网站中很多重要的信息都需要保存到数据库中.如用户名.密码等等其他信息.Django框架是一个基于MVT思想的框架,也就是说他本身就已经封装了Model类 ...

  5. 初识Flask框架,以及Flask中的模板语言jinjia2和Flask内置的Session

    一.web框架的对比 首先我们先来看下比较火的web框架 1.Django: 优点:大而全,所有组件都是组织内部开发高度定制化,教科书级别的框架 缺点:大到浪费资源,请求的时候需要的资源较高 2.Fl ...

  6. Python框架学习之用Flask创建一个简单项目

    在前面一篇讲了如何创建一个虚拟环境,今天这一篇就来说说如何创建一个简单的Flask项目.关于Flask的具体介绍就不详细叙述了,我们只要知道它非常简洁.灵活和扩展性强就够了.它不像Django那样集成 ...

  7. Flask初学者:Jinja2模板

    Python的Jinja2模板,其实就是在HTML文档中使用控制语句和表达语句替换HTML文档中的变量来控制HTML的显示格式,Python的Jinja2模板可以更加灵活和方便的控制HTML的显示,而 ...

  8. Flask中的request模板渲染Jinja以及Session

    Flask中的request与django相似介绍几个常用的以后用的时候直接查询即可 1.request from flask import request(用之前先引用,与django稍有不同) r ...

  9. StrangeIoc框架学习----在项目中实战

    最近,因为公司的项目一直在研究StrangeIoc框架,小有所得,略作记录. StrangeIoc是一款基于MVCS的一种框架,是对MVC思想的扩展,是专门针对unity开发的一款框架,非常好用. 一 ...

随机推荐

  1. sql片段

    1):定义sql片段 <!-- 定义sql片段 --> <!-- id: sql片段的标识 经验:1:基于单表来定义sql片段,这样的话sql片段的可重用性才高 2:sql片段中不要 ...

  2. Linux 安装 jdk8

    切换目录 cd /usr 创建目录 mkdir java cd java 下载 jdk rz 或者 ftp 都行,只要能成功上传 解压 tar zxvf jdk-8u181-linux-x64.tar ...

  3. 安装docker17.06.0版本报错和解决方法

    本人在自己电脑的虚拟机里安装docker ce 17.06.0版本的时候报如下错误: [root@manager2 yum.repos.d]# yum install docker-ce-17.06. ...

  4. Android--底部导航栏的动态替换方案

    1.通常来说,一般情况下,我们的app的BottomTab会有集中实现方式. 自定义view,然后自己写逻辑去实现互斥. 自由度最高,因为啥都是自己写的. 使用RadioGroup+RadioButt ...

  5. MFC Bresesnham算法

    Bresesnham算法绘制直线段 Bresenham算法的意义:高效的将图形光栅化.其计算过程中均采用加法运算,故大大减少了程序的开销. 绘制直线段(MFC中) //传入参数:起点.终点,颜色 vo ...

  6. python模块--collections

    python的内建模块collections有几个关键的数据结构,平常在使用的时候,开发者可以直接调用,不需要自己重复制造轮子,这样可以提高开发效率. 1. deque双端队列 平常我们使用的pyth ...

  7. (python)数据结构---字典

    一.描述 由键值key-value组成的数据的集合 可变.无序的,key不可以重复 字典的键key要可hash(列表.字典.集合不可哈希),不可变的数据结构是可哈希的(字符串.元组.对象.bytes) ...

  8. 同一个菜品商家中心和erp价格显示不一致解决方案FAQ

    1.适用场景: 2.问题原因:子账号在商家中心改了价格 3.解决办法: (1).子账号登录商家后台修改 再同步(2).ERP上商品管理 修改价格

  9. Spark WordCount 文档词频计数

    一.使用数据 Apache Spark is a fast and general-purpose cluster computing system.It provides high-level AP ...

  10. Scala隐式参数

    Scala方法可以具有隐式参数列表,由参数列表开头的implicit关键字标记.如果参数列表中的参数没有像往常一样传递,Scala将查看它是否可以获得正确类型的隐式值,如果可以,将自动传递. Scal ...