Flask模版详解

Flask模版详解

  • 概述
  • Jinja2模板引擎
    • 渲染模版的步骤
    • 变量
    • 控制结构
    • 自定义错误页面
    • 链接
    • 静态文件

概述

模板是一个包含响应文本的文件,其中包含用占位变量表示的动态部分,其具体值只在请求的上下文中才能知道。使用真实值替换变量,再返回最终得到的响应字符串,这一过程称为渲染。为了渲染模板,Flask 使用了一个名为 Jinja2 的强大模板引擎

形式最简单的 Jinja2 模板就是一个包含响应文本的文件,例如:

<h1>Hello, {{ name }}!</h1>

Jinja2模板引擎

渲染模版的步骤

1、前端创建模版

默认情况下,Flask 在程序文件夹中的 templates 子文件夹中寻找模板。例如把前面定义的模板保存在templates 文件夹中,命名为index.html:

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Index</title>
</head>
<body>
<h1>Hello, {{ name }}!</h1>
</body>
</html>

2、后端渲染模版

@app.route('/')
def index():name = "dahezhiquan"return render_template('index.html', name=name)

Flask 提供的 render_template 函数把 Jinja2 模板引擎集成到了程序中。render_template 函数的第一个参数是模板的文件名。随后的参数都是键值对,表示模板中变量对应的真实值。在这段代码中,第二个模板收到一个名为 name 的变量

左边的“name”表示参数名,就是模板中使用的占位符;右边的“name”是当前作用域中的变量,表示同名参数的值

3、运行程序,查看模版渲染效果

image.png

变量

在模板中使用的{{ name }}结构表示一个变量,它是一种特殊的占位符,告诉模板引擎这个位置的值从渲染模板时使用的数据中获取

Jinja2 能识别所有类型的变量,甚至是一些复杂的类型,例如列表、字典和对象。在模板中使用变量的一些示例如下:

<!-- 从字典中获取值 -->
<p>A value from a dictionary: {{ mydict['key'] }}.</p><!-- 从列表中获取值 -->
<p>A value from a list: {{ mylist[3] }}.</p><!-- 从列表中获取值,使用变量作为索引 -->
<p>A value from a list, with a variable index: {{ mylist[myintvar] }}.</p><!-- 调用对象的方法 -->
<p>A value from an object's method: {{ myobj.somemethod() }}.</p>

同时还可以使用过滤器修改变量,过滤器名添加在变量名之后,中间使用竖线分隔,例如,下述模板以首字母大写形式显示变量 name 的值:

Hello, {{ name|capitalize }}

Jinja2 提供的部分常用过滤器:

  • safe:标记变量为安全,使得它们不会被转义。例如:{{ my_html_content | safe }}
  • capitalize:将字符串的首字母大写。例如:{{ my_string | capitalize }}
  • lower:将字符串转换为小写。例如:{{ my_string | lower }}
  • upper:将字符串转换为大写。例如:{{ my_string | upper }}
  • title:将字符串中每个单词的首字母大写。例如:{{ my_string | title }}
  • trim:除字符串两侧的空白字符。例如:{{ my_string | trim }}
  • striptags:移除所有 HTML 标签,并仅保留纯文本内容

safe 过滤器值得特别说明一下。默认情况下,出于安全考虑,Jinja2 会转义所有变量。例如,如果一个变量的值为 ‘<h1>Hello</h1>’,Jinja2 会将其渲染成’&lt;h1&gt;Hello&lt;/h1&gt;',浏览器能显示这个 h1 元素,但不会进行解释。很多情况下需要显示变量中存储的 HTML 代码,这时就可使用 safe 过滤器。千万别在不可信的值上使用 safe 过滤器,例如用户在表单中输入的文本。

控制结构

Jinja2 提供了多种控制结构,可用来改变模板的渲染流程,例如:

{% if user %}Hello, {{ user }}!
{% else %}Hello, stranger!
{% endif %}

另一种常见需求是在模板中渲染一组元素。下例展示了如何使用 for 循环实现这一需求:

<ul>
{% for comment in comments %}<li>{{ comment }}</li>
{% endfor %}
</ul>

Jinja2 还支持宏。宏类似于 Python 代码中的函数。例如:

{% macro render_comment(comment) %}<li>{{ comment }}</li>
{% endmacro %}<ul>
{% for comment in comments %}{{ render_comment(comment) }}
{% endfor %}
</ul>

在这个模板中,{% macro render_comment(comment) %} 定义了一个宏,它接受一个名为 comment 的参数,并返回一个 <li> 标签,其中包含评论内容。{% endmacro %} 表示宏定义的结束。

然后,在循环中,{% for comment in comments %} 遍历评论列表,并对每个评论调用 render_comment 宏来生成相应的 HTML。每次循环迭代时,宏将被展开,生成一个包含评论内容的列表项,并将其插入到 <ul> 中。

这种使用宏的方式可以使模板更具可重用性和可维护性,特别是当需要在多个地方使用相同的 HTML 结构时。

需要在多处重复使用的模板代码片段可以写入单独的文件,再包含在所有模板中,以避免重复:

{% include 'common.html' %}

另一种重复使用代码的强大方式是模板继承,它类似于 Python 代码中的类继承。首先,创建一个名为 base.html 的基模板:

<html lang="zh-CN">
<head>{% block head %}<title>{% block title %}{% endblock %} - My Application</title>{% endblock %}
</head>
<body>{% block body %}{% endblock %}
</body>
</html>

在这个模板中,{% block head %} {% block body %} 标记定义了两个可替换的块,它们分别用于定义页面头部和主体内容

下面这个示例是基模板的衍生模板:

{% extends "base.html" %}{% block title %}Index
{% endblock %}{% block head %}{{ super() }}<style></style>
{% endblock %}{% block body %}<h1>Hello, World!</h1>
{% endblock %}

在这个子模板中,使用了 {% extends "base.html" %} 来继承基础模板。然后,重写了 title 块,将页面标题设置为 “Index”。接着,重写了 head 块,在原有的基础上使用了 super() 函数来调用基础模板中定义的内容,并添加了特定页面的样式。最后,重写了 body 块,定义了页面的主体内容

image.png

自定义错误页面

如果你在浏览器的地址栏中输入了不可用的路由,那么会显示一个状态码为 404 的错误页面
像常规路由一样,Flask 允许程序使用基于模板的自定义错误页面。最常见的错误代码有两个:404,客户端请求未知页面或路由时显示;500,有未处理的异常时显示

1、编写视图代码

@app.errorhandler(404)
def page_not_found(e):return render_template('errors/404.html'), 404@app.errorhandler(500)
def internal_server_error(e):return render_template('errors/500.html'), 500

2、编写错误模版代码

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

3、此时访问一个不存在的URL,会呈现自定义的404模版页面

image.png

链接

任何具有多个路由的程序都需要可以连接不同页面的链接,例如导航条。

在模板中直接编写简单路由的 URL 链接不难,但对于包含可变部分的动态路由,在模板中构建正确的 URL 就很困难。而且,直接编写 URL 会对代码中定义的路由产生不必要的依赖关系。如果重新定义路由,模板中的链接可能会失效。

为了避免这些问题,Flask 提供了 url_for() 辅助函数,它可以使用程序 URL 映射中保存的信息生成 URL。

url_for('index') 得到的结果是 /。调用 url_for('index', _external=True) 返回的则是绝对地址,例如:http://127.0.0.1:5000/

使用 url_for() 生成动态地址时,将动态部分作为关键字参数传入。例如:

url = url_for('index', name='john', _external=True)

上述代码的返回结果是,http://127.0.0.1:5000/index?name=john

静态文件

Web 程序不是仅由 Python 代码和模板组成。大多数程序还会使用静态文件,例如HTML代码中引用的图片、JavaScript 源码文件和 CSS

默认设置下,Flask 在程序根目录中名为 static 的子目录中寻找静态文件。如果需要,可在 static 文件夹中使用子文件夹存放文件

1、在项目的static文件夹中上传icon网页图标文件

image.png

2、在base.html中使用favicon.ico

<html lang="zh-CN">
<head>{% block head %}<title>{% block title %}{% endblock %} - My Application</title>{% endblock %}<link rel="shortcut icon" href="{{ url_for('static', filename='favicon.ico') }}" type="image/x-icon"><link rel="icon" href="{{ url_for('static', filename='favicon.ico') }}" type="image/x-icon">
</head>
<body>{% block body %}{% endblock %}
</body>
</html>

3、icon图标设置成功

image.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/660986.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

公考学习平台|基于SprinBoot+vue的公考学习平台(源码+数据库+文档)

公考学习平台目录 目录 基于SprinBootvue的公考学习平台 一、前言 二、系统设计 三、系统功能设计 5.1用户信息管理 5.2 视频信息管理 5.3公告信息管理 5.1论坛信息管理 四、数据库设计 五、核心代码 六、论文参考 七、最新计算机毕设选题推荐 八、源码获取&…

【C++】:类和对象(下)

目录 一&#xff0c;再谈构造函数1.初始化列表2. 隐式类型转换的过程及其优化3. 隐式类型转换的使用4. explcit关键字5. 单参数和多参数构造函数的隐式类型转换 二&#xff0c;static成员1.静态成员变量2.静态成员函数 三&#xff0c;友元3.1 友元函数3.2 友元类 四&#xff0c…

慧言AIVoceChat实现在线客服及社区频道

原文链接&#xff1a;小回博客 慧言AI&VoceChat实现在线客服及社区频道 一、VoceChat 简介 官网&#xff1a;https://voce.chat VoceChat 是一款支持独立部署的个人云社交媒体聊天服务。15MB 的大小可部署在任何的服务器上&#xff0c;部署简单&#xff0c;很少需要维护…

IoTDB 入门教程①——时序数据库为什么选IoTDB ?

文章目录 一、前文二、性能排行第一三、完全开源四、数据文件TsFile五、乱序数据高写入六、其他七、参考 一、前文 IoTDB入门教程——导读 关注博主的同学都知道&#xff0c;博主在物联网领域深耕多年。 时序数据库&#xff0c;博主已经用过很多&#xff0c;从最早的InfluxDB&a…

UNI-APP_拨打电话权限如何去掉,访问文件权限关闭

uniapp上架过程中一直提示&#xff1a;允许“app名”拨打电话和管理通话吗&#xff1f; uniapp配置文件&#xff1a;manifest.json “permissionPhoneState” : {“request” : “none”//拨打电话权限关闭 }, “permissionExternalStorage” : {“request” : “none”//访…

C++-9

C 1.已知C风格的字符串&#xff0c;完成对字符串通过下标访问时的异常处理机制(越界访问) 2.写一个程序&#xff0c;程序包含两个类&#xff0c;类中实现一个成员函数&#xff0c;MyGetChar(), 类A中每调用一 次&#xff0c;按顺序得到一个数字字符&#xff0c;比如第-次调用得…

开源AI名片商城系统小程序:智能管理引领营销新潮流

在当今数字化时代&#xff0c;如何高效地管理客户关系、提升营销效果&#xff0c;成为了企业关注的焦点。开源AI名片商城系统小程序凭借其智能化管理功能&#xff0c;为企业提供了一个全新的解决方案。 一、访客画像&#xff1a;精准洞察&#xff0c;个性化内容培育 该系统能够…

SpringMVC整体工作流程

. 用户发起一个请求&#xff0c;请求首先到达前端控制器前端控制器接收到请求后会调用处理器映射器&#xff0c;由此得知&#xff0c;这个请求该由哪一个Controller来进行处理(并未调用Controller)&#xff1b;前端控制器调用处理器适配器&#xff0c;告诉处理器适配器应该要…

能源监控新方案:IEC104转MQTT网关在新能源发电中的应用

需求背景 近些年&#xff0c;我国新能源产业快速发展&#xff0c;光伏、风电等新能源项目高速增长&#xff0c;新能源发电已经成为国家能源结构的重要组成部分。 打造数字化、智能化、信息化的电力物联网系统&#xff0c;实现光伏风电等新能源发电站的远程监控、远程维护是新能…

C++必修:类与对象(二)

✨✨ 欢迎大家来到贝蒂大讲堂✨✨ &#x1f388;&#x1f388;养成好习惯&#xff0c;先赞后看哦~&#x1f388;&#x1f388; 所属专栏&#xff1a;C学习 贝蒂的主页&#xff1a;Betty’s blog 1. 构造函数 1.1. 定义 构造函数是一个特殊的成员函数&#xff0c;名字与类名相…

【webrtc】MessageHandler 6: 基于线程的消息处理:StunRequest实现包发送和超时重传

G:\CDN\rtcCli\m98\src\p2p\base\stun_request.cc使用OnMessage 实现包的发送和包的超时重传StunRequest 一个StunRequest 代表是一个独立的请求的发送STUN消息 要不是发送前构造好的,要不就是按照需要构建的使用StunRequestManager: 每一个STUNRequest 携带一个交互id 写入m…

神经网络反向传播算法

今天我们来看一下神经网络中的反向传播算法&#xff0c;之前介绍了梯度下降与正向传播~ 神经网络的反向传播 专栏&#xff1a;&#x1f48e;实战PyTorch&#x1f48e; 反向传播算法&#xff08;Back Propagation&#xff0c;简称BP&#xff09;是一种用于训练神经网络的算…