flask框架渲染Jinja模板与传入模板变量操作详解


Posted in Python onJanuary 25, 2020

本文实例讲述了flask框架渲染Jinja模板与传入模板变量操作。分享给大家供大家参考,具体如下:

1. 模板简介

模板是一个web开发中必备的模块,因为我们在渲染一个网页的时候,并不只是渲染了一个纯文本字符窜,而是渲染一个有富文本标签的页面,这个时候我们就需要用到模板了。在flask中,配套的模板是Jinja2,Jinja2的作者也是flask的作者。

2. flask中渲染模板

在flask中,如果我们需要渲染一个模板,那么我们就需要用到render_template这个方法了。

在我们新建一个flask项目的时候,会同时生成一个templates的文件夹,然后我们就在里面新建一个index.html的文件。然后写入测试代码:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>index</title>
</head>
<body>
 <h1>index</h1>
</body>
</html>

然后我们在app.py文件中写一个视图函数渲染我们的index.html文件。

from flask import render_template
@app.route('/index/')
def index():
  return render_template('index.html')

这样,我们就成功的对html页面进行了渲染。然后我们运行项目,输入网址就能够查看到效果了。

3. flask中模板文件查找路径

在上面的render_template函数中,为什么我们直接写入index.html,flask就会知道去templates文件夹里面去找这个文件呢。而不是去其他位置查找index.html文件呢。这是因为在flask中,默认的查找模板路劲就在项目的根目录下面的templates文件夹。所以当我们写模板文件的时候,都会写在templates下面。

在flask中,我们也是可以修改模板的存放位置的,比如我们将模板文件存放位置修改为E:\templates,那么我们就可以这样写。

from flask import Flask,render_template
app = Flask(__name__,template_folder=r'E:\templates')

这样,flask每次查找模板文件路径的时候,就回去这个文件夹下面寻找,如果没有找到,就会报一个jinja2.exceptions.TemplateNotFound的错误,所以,当我们遇到了这个错误的时候,我们就要知道是哪个位置出问题了。

4. 模板中传入参数

在一个模板中,我们不可避免的会传入一些参数,那么在flask中,应该怎样闯入参数呢。

首先编写一个视图,然后在render_template中传入一个关键字参数,例如下面的username=‘xxx'

from flask import render_template
@app.route('/index/')
def index():
  return render_template('index.html',username='xxx')

然后我们在模板中怎样使用这个变量呢?我们在index.html中写入以下代码

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>index</title>
</head>
<body>
 <h1>index</h1>
 <p>userneme: {{ username }}</p>
</body>
</html>

所以,我们在模板中通过 {{ username }}就可以拿到我们冲视图中传入的值了。也就是说,在Jinja2模板中,是通过{{ 变量名 }}来获取数据的,如果我们在{{ }}中传入了一个视图并没有穿给我们的变量,那么也不会报错,只是什么都不显示而已。

如果我们需要传入多个参数,只需要依次在render_template函数中传入我们的关键之参数就可以了。
示例:

return render_template('index.html',username='xxx',age=18,...)

但是如果我们参数很多的话,那么这样我们也不方便我们管理和查看,这个时候我们就可以换一种方式了,定义一个字典,来存放所有的变量,然后在传入模板中

示例:

@app.route('/index/')
def index():
 context = {
 'username':'xxx',
 'age':18,
 'height':180,
 }
  return render_template('index.html',context=context)

但是这个时候,当我们在模板找中直接输入{{ username }},{{ age }}, {{ height }}的时候,是获取不到我们的数据的,因为我们使用这种方法的话,在模板中,获取参数就需要改变一下方式了。变成下面这样.

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>index</title>
</head>
<body>
 <h1>index</h1>
 <p>userneme: {{ context.username }}</p>
 <p>userneme: {{ context['age'] }}</p>
 <p>userneme: {{ context.height }}</p>
</body>
</html>

在上面模板中,我们使用了两种方式得到参数,context['username']和context.username。因为context是一个字典,所以使用这两种方法都是可以的。

但是这样我们仍然觉得不方便,每次都需要通过context才能获取到我们传入的参数。那么我们可不可以不通过context才能获取参数呢,答案是可以的。

实例:

@app.route('/index/')
def index():
 context = {
 'username':'xxx',
 'age':18,
 'height':180,
 }
  return render_template('index.html',**context)

我们在视图函数中这样写,我们就需要通过context才能得到我们的参数了。

**context其实就是将这个字典打撒开来,形成关键字参数。所以,他和下面这种写法是完全一样的。

@app.route('/index/')
def index():
  return render_template('index.html',username='xxx',age=18,height=180)

一般我们在项目的开发中,我们都是使用**context这种写法。

当然,在我们的实际开发中,传送的数据肯定不是这么简单,一般都有数据嵌套之类的,还有对象。
例如下面这样:

# 定义一个Person类
class Person():
  def __init__(self,name,age):
    self.name = name
    self.age = age
person = Person('小明', 18) # 实例化一个Person对象
@app.route('/')
def index():
  context = {
    'username':'xujin',
    'age':18,
    'children':{
      'name':'hah',
      'height':190,
    },
    'person':person,
    'list':[1,2,3]
  }
  return render_template('index.html',**context)

其实在Jinja2模板中,我们对数据的操作和在python都是差不多的,像上面这种数据,我们就可以通过下面的方式来获取。

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>index</title>
</head>
<body>
<h1>index</h1>
hello {{ username }}
<p> {{ children.name}} </p>
<p> {{ children['height'] }} </p>
{{ person }}
{{ person.name }}
{{ person.age }}
{{ list }}
{{ list[1] }}
</body>
</html>

5. url_for的使用

在模板中,我们一般也少不了需要url地址,而我们直接手动写入url地址的话,不方便我们后面的管理,所以一般我们都会使用url_for函数构造我们的url。

比如我们有一个login页面,然后我么需要从首页点击登录之后,就跳转至login页面,那么我们需要这样做。

@app.route('/login/')
def login():
  return "这是login页面"
@app.route('/index/')
def login():
  return render_template('index.html')

然后我们在index.html中写入

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>index</title>
</head>
<body>
<h1>index</h1>
<p><a href="/login/" rel="external nofollow" >登陆</a></p>
<p><a href="{{ url_for('login') }}" rel="external nofollow" >登陆</a></p>
</body>
</html>

上面两种方式一种是直接写死url的方式,一种就是使用url_for的的方式。一般我们都是会使用url_for这种方式的。

如果我们的url需要参数,那么其实和在视图中传入参数是一样的。

示例:

@app.route('/user/<int:user_id>/')
def user(user_id):
 return "user id is %s " % user_id

模板文件中写入

<a href="{{ url_for('user',user_id=1,next='xxx') }}" rel="external nofollow" >user</a>
<!-- 等价于下面这样 -->
<a href="/user/1/?next=xxx" rel="external nofollow" >user</a>

希望本文所述对大家基于flask框架的Python程序设计有所帮助。

Python 相关文章推荐
Python显示进度条的方法
Sep 20 Python
Python调用C语言开发的共享库方法实例
Mar 18 Python
python传递参数方式小结
Apr 17 Python
Python实现删除文件但保留指定文件
Jun 21 Python
Python爬虫使用Selenium+PhantomJS抓取Ajax和动态HTML内容
Feb 23 Python
Python实现爬取马云的微博功能示例
Feb 16 Python
详解python解压压缩包的五种方法
Jul 05 Python
PYQT5开启多个线程和窗口,多线程与多窗口的交互实例
Dec 13 Python
python在不同条件下的输入与输出
Feb 13 Python
Python datetime模块使用方法小结
Jun 18 Python
如何在windows下安装配置python工具Ulipad
Oct 27 Python
python 实现aes256加密
Nov 27 Python
如何在 Django 模板中输出 &quot;{{&quot;
Jan 24 #Python
在keras中获取某一层上的feature map实例
Jan 24 #Python
keras获得model中某一层的某一个Tensor的输出维度教程
Jan 24 #Python
使用Tensorflow实现可视化中间层和卷积层
Jan 24 #Python
tensorflow获取预训练模型某层参数并赋值到当前网络指定层方式
Jan 24 #Python
keras获得某一层或者某层权重的输出实例
Jan 24 #Python
浅谈keras的深度模型训练过程及结果记录方式
Jan 24 #Python
You might like
phpmyadmin 常用选项设置详解版
2010/03/07 PHP
php版小黄鸡simsimi聊天机器人接口分享
2014/01/26 PHP
PHP实现微信网页授权开发教程
2016/01/19 PHP
PHP加密技术的简单实现
2016/09/04 PHP
微信 getAccessToken方法详解及实例
2016/11/23 PHP
php实现base64图片上传方式实例代码
2017/02/22 PHP
PHP 99乘法表的几种实现代码
2020/10/13 PHP
传智播客学习之java 反射
2009/11/22 Javascript
用Javascript评估用户输入密码的强度实现代码
2011/11/30 Javascript
JSON+JavaScript处理JSON的简单例子
2013/03/20 Javascript
二叉树的非递归后序遍历算法实例详解
2014/02/07 Javascript
jQuery实现鼠标滚轮动态改变样式或效果
2015/01/05 Javascript
JS+CSS实现模仿浏览器网页字符查找功能的方法
2015/02/26 Javascript
jQuery使用toggleClass方法动态添加删除Class样式的方法
2015/03/26 Javascript
超实用的JavaScript表单代码段
2016/02/26 Javascript
Angular2表单自定义验证器的实现
2016/10/19 Javascript
利用angular、react和vue实现相同的面试题组件
2018/02/19 Javascript
详解如何使用webpack打包JS
2018/06/21 Javascript
一文快速详解前端框架 Vue 最强大的功能
2019/05/21 Javascript
JS 设计模式之:工厂模式定义与实现方法浅析
2020/05/06 Javascript
Vue过滤器,生命周期函数和vue-resource简单介绍
2021/01/12 Vue.js
Python排序算法之选择排序定义与用法示例
2018/04/29 Python
Python简单读写Xls格式文档的方法示例
2018/08/17 Python
python匹配两个短语之间的字符实例
2018/12/25 Python
对python多线程中互斥锁Threading.Lock的简单应用详解
2019/01/11 Python
Python设计模式之适配器模式原理与用法详解
2019/01/15 Python
python 定义类时,实现内部方法的互相调用
2019/12/25 Python
Python如何实现小程序 无限求和平均
2020/02/18 Python
西班牙著名的珠宝首饰品牌:P D PAOLA
2018/09/15 全球购物
PHP面试题-$message和$$message的区别
2015/12/08 面试题
北京华建集团SQL面试题
2014/06/03 面试题
英语专业毕业生自我鉴定
2013/11/09 职场文书
《梅兰芳学艺》教学反思
2014/02/24 职场文书
公司门卫岗位职责
2014/03/15 职场文书
教师业务学习材料
2014/12/16 职场文书
勤俭节约主题班会
2015/08/13 职场文书