文档章节

(二)Flask初体验——模板

AllenOR灵感
 AllenOR灵感
发布于 2017/09/10 01:19
字数 1778
阅读 3
收藏 0

Flask 学习目录

(一)Flask初体验——Hello World
(二)Flask初体验——模板
(三)Flask初体验——web 表单


如果你已经学习了前面的 Hello World 章节,那么你应该已经有了一个完全工作的简单的 web 应用程序,它的文件结构如下:

microblog/
├── app
│   ├── __init__.py
│   ├── __init__.pyc
│   ├── static
│   ├── templates
│   ├── views.py
│   └── views.pyc
├── run.py
└── tmp

在 Python 中生成 HTML 代码并不简单,而且非常麻烦,因为你必须自行做好 HTML 转义以保持应用程序的安全。由于这个原因,Flask 自动为你配置好 Jinja2 模板。所以在这里我们介绍一下模板的基本概念以及基本用法。

为什么我们需要模板

让我们来考虑一下我们该如何扩充这个小的应用程序。

我们希望我们的微博应用程序的主页上有一个欢迎登录用户的标题,而且这是这种类型的应用程序的一个“标配”。

输出一个漂亮的大标题的一个容易的选择就是改变我们的视图功能,输出 HTML ,也许像这个样子:

#!/usr/bin/env python
# -*- coding: utf-8 -*-

from app import app

@app.route('/')
@app.route('/index')

def index():
    user = { 'nickname': 'Miguel' } # fake user
    return '''
            <html>
              <head>
                <title>Home Page</title>
              </head>
              <body>
                <h1>Hello, ''' + user['nickname'] + '''</h1>
              </body>
            </html>
            '''

接着你运行看看浏览器上的显示情况,如下图:


因为我们暂时还不支持用户,所以暂时使用了占位符的用户对象,有时也被成为假冒或模仿的对象。这样让我们可以集中关注应用程序的磨一方面,而不用花心思在暂未完成的部分上面。

但是,上面的解决方案是非常难看的,而且如果你需要构建一个大型的网站,那么其中就会设计到大量的复杂的 HTML 页面,这样就会使代码非常复杂。所以,Flask 为我们准备了 Jinja2 模板。接下来,我们学习一下 Jinja2 模板。

模板从天而降

如果你能够保持你的应用程序与网页的布局或者界面逻辑上是分开的,这样不是显得更加容易组织?难道你不觉得是这样吗?而模板可以帮助实现这种分离。

让我们编写第一个我们的模板,文件位置是 app/templates/index.html

<html>
  <head>
    <title>{{title}} - microblog</title>
  </head>
  <body>
      <h1>Hello, {{user.nickname}}!</h1>
  </body>
</html>

正如你在上面看到的,我们只是写了一个大部分标准的 HTML 页面,唯一的区别是有一些动态内容的在 {{...}} 中。

现在看看怎样在我们的视图函数中使用这些模板,文件位置是 app/views.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-

from app import app
from flask import render_template

@app.route('/')
@app.route('/index')

def index():
    user = { 'nickname': 'Miguel' } # fake user
    return render_template("index.html",
            title = 'Home',
            user = user)

试着运行下应用程序看看模板是如何工作的。一旦在你的浏览器上呈现该网页,你可以浏览下 HTML 源代码,与原始的模板内容对比下差别。

为了渲染模板,我们必须从 Flask 框架中导入一个名为 render_template 的新函数。此函数需要传入模板名以及一些模板变量列表,返回一个所有变量被替换的渲染的模板。

在内部,render_template 调用了 Jinja2 模板引擎,Jinja2 模板引擎是 Flask 框架的一部分。Jinja2 会把模板参数提供的相应的值替换了 {{...}} 块。

模板中控制语句

Jinja2 模板同样支持控制语句,像在 {{...}} 块中。让我们在我们的模板中添加一个 if 声明,文件位置是 app/templates/index.html

<html>
  <head>
      {% if title %}
    <title>{{title}} - microblog</title>
    {% else %}
    <title>Welcome to microblog</title>
    {% endif %}
  </head>
  <body>
      <h1>Hello, {{user.nickname}}!</h1>
  </body>
</html>

现在我们的模板变得更加智能了。如果视图函数忘记输入页面标题的参数,也不会出发异常反而会出现我们自己提供的标题。放心地去掉视图函数中 render_template 的调用中的 title 参数,看看 if 语句是如何工作的!

模板中的循环语句

在我们 microblog 应用程序中,登录的用户想要在首页展示他的或者她的联系人列表中用户最近的文章,因此让我们看看如何才能做到。

首先我们先创建一些用户以及他们的文章用来展示,文件位置是 app/views.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-

from app import app
from flask import render_template

@app.route('/')
@app.route('/index')

def index():
    user = { 'nickname': 'Miguel' } # fake user
    # 其实这里可以从数据库中读取,然后在前端显示
    posts = [
        {
            'author': {'nickname': 'John'},
            'body': 'Beautiful day in Portland!'
        },
        {
            'author': {'nickname': 'Susan'},
            'body': 'The Avengers movie was so cool!'
        }
    ]
    return render_template("index.html",
            title = 'Home',
            user = user,
            posts = posts)

在使用模板这一方面,我们必须解决一个新问题。列表中可能有许多元素,多少篇文章被展示将取决于视图函数。模板不会假设有多少文章,因此它必须准备渲染视图传送的文章数量。

因此让我们来看看怎么使用 for 来做到这一点,文件位置是 app/templates/index.html

<html>
  <head>
      {% if title %}
    <title>{{title}} - microblog</title>
    {% else %}
    <title>Welcome to microblog</title>
    {% endif %}
  </head>
  <body>
      <h1>Hello, {{user.nickname}}!</h1>
      {% for post in posts %}
      <p>{{post.author.nickname}} says: <b>{{post.body}}</b></p>
      {% endfor %}
  </body>
</html>

接着你可以在浏览器中试试,可以看到以下页面:


模板继承

在我们的 microblog 应用程序中,在页面的顶部需要一个导航栏。在导航栏里面有编辑账号,登出等等的链接。

我们可以在 index.html 模板中添加一个导航栏,但是随着应用的扩展,越来越多的模板需要这个导航栏,我们需要在每一个模板中复制这个导航栏。然而你必须要保证每一个导航栏都要同步,如果你有大量的模板,这需要花费很大的力气。

相反,我们可以利用 Jinja2 的模板集成的特点,这允许我们把所有模板公共的部分移除出页面的布局,接着把我们放在一个基础模板中,所有使用它的模板可以导入这个基础模板。

所有让我们定义一个基础模板,爱模板包含导航栏以及上面谈论的标题,文件位置是 app/templates/base.html

<html>
  <head>
      {% if title %}
    <title>{{title}} - microblog</title>
    {% else %}
    <title>Welcome to microblog</title>
    {% endif %}
  </head>
  <body>
      <div>Microblog: <a href="/index">Home</a></div>
      <hr>
      {% block content %}
      {% endblock %}
  </body>
</html>

在这个模板中,我们使用 block 控制语句来定义派生模板可以出入的地方,块被赋予唯一的名字。

接下来,我们需要修改我们的 index.html 模板,来继承来自 base.html 文件,index.html 文件位置是 app/templates/index.html

{% extends "base.html" %}
{% block content %}
    <h1>Hello, {{user.nickname}}!</h1>
    {% for post in posts %}
    <p>{{post.author.nickname}} says: <b>{{post.body}}</b></p>
    {% endfor %}
{% endblock %}

接下来,你可以尝试运行一下这个程序,你可以看到以下页面:


至此,我们学会了如何使用 Jinja2 模板来编写前端网页。


参考资料:

Flask 模板

Flask 文档

本文转载自:http://www.jianshu.com/p/1e5b66f58945

共有 人打赏支持
AllenOR灵感
粉丝 10
博文 2634
码字总数 82983
作品 0
程序员
看完这篇文章还能不懂Flask这种Web框架吗?

Flask是一个基于Python开发并且依赖jinja2模板和Werkzeug WSGI服务的一个微型框架,对于Werkzeug本质是Socket服务端,其用于接收http请求并对请求进行预处理,然后触发Flask框架,开发人员基...

lemonwater
05/14
0
0
Flask從入門到入土(三)——模板

  模板是一個包含響應文本的文件,其中包含佔位變量表示的動態部分,其具體值只是請求上下文中才能知道。使用真實值替換變量,再返回最終得到的響應字符串,這一過程稱爲渲染。爲了渲染模板...

奶berber
01/21
0
0
Flask 使用小结【Updating】

1、最简单的hello world #!/usr/bin/env python encoding: utf-8 from flask import Flaskapp = Flask(name) @app.route('/')def index(): return 'hello world' if name == 'main': app.ru......

大数据之路
2013/10/24
0
0
flask(一)jinja模板

1、flask的默认模板是jinja ,模板默认目录是你开发的应用目录下的templates ,例:app/templates 2、导入模板传递函数包 :from flask import render_template render——template(argumen...

ricardohn
2016/11/07
10
0
(二)Flask 学习 —— 模板

模板 回顾 如果你依照 Hello World 这一章的话,你应当有一个完全工作的简单的 web 应用程序,它有着如下的文件结构: microblogflask <virtual environment files>app static templates init...

水果糖
2016/02/25
239
0

没有更多内容

加载失败,请刷新页面

加载更多

CentOS7+rsync+sersync实现数据实时同步

一、为什么要用Rsync+sersync架构? 1、sersync是基于Inotify开发的,类似于Inotify-tools的工具 2、sersync可以记录下被监听目录中发生变化的(包括增加、删除、修改)具体某一个文件或某一个...

linjin200
8分钟前
0
0
兄弟连区块链入门教程eth源码分析p2p-udp.go源码分析(二)

ping方法与pending的处理,之前谈到了pending是等待一个reply。 这里通过代码来分析是如何实现等待reply的。 pending方法把pending结构体发送给addpending. 然后等待消息的处理和接收。 ...

兄弟连区块链入门教程
17分钟前
0
0
忘了Python关键语句?这份备忘录拯救你的记忆

今天要介绍的 Python 3 Cheat Sheet 由法国国家科学研究中心(CNRS)的法国机械工程与信息技术实验室(LIMSI)的工程师 Laurent Pointal 总结。这个简单的 Cheat Sheet 专注于从算法/编程开始...

酒逢知己千杯少
19分钟前
0
0
MarkDown转Html在线转换(支持代码高亮,可复制到公众号、今日头条)

MarkDown/Html在线转换能够将md渲染成html并且能保持代码高亮,可以方便的复制待格式的html粘贴到公众号,CSDN,简书,博客园,开源中国等。 扫码体验在线助手小程序 我是java代码 public s...

陈守印
19分钟前
0
0
人工智能视频教程下载

百度网盘学习资源 链接:https://pan.baidu.com/s/1DxkxKIGOagK5Jg9bEzFC0w 提取码:8pra 链接:https://pan.baidu.com/s/1_MmaaTiVdz6PabyWTGF4Vw 提取码:vjg7 更多视频资料 可关注微信公众...

dominic69
29分钟前
1
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部