文章目錄
- 模闆
-
- jinja2介紹
- jinja2的優點
- 安裝jinja2
-
- jinja2文法
- 基本文法
- jinja2變量
- jinja2中的過濾器
- jinja2的控制結構
- jinja2的for循環
-
- 疊代清單
- 疊代字典
- jinja2的宏
- jinja2的繼承和Super函數
- 利用jinja2進行渲染
-
- 基本使用方法
-
- PackageLoader
- FileSystemLoader
模闆
要了解jinja2,那麼需要先了解模闆的概念。模闆在Python的web開發中廣泛使用,它能夠有效的将業務邏輯和頁面邏輯分開,使代碼可讀性增強、并且更加容易了解和維護。
模闆簡單來說就是一個其中包涵占位變量表示動态的部分的檔案,模闆檔案在經過動态指派後,傳回給使用者。 --> 可以了解為渲染
python中自帶一個簡單的模闆,就是string提供的。
>>> import string
>>> a = string.Template('$who is $role')
>>> a.substitute(who='daxin',role='Linux')
'daxin is Linux'
>>> a.substitute(who='daxin',role='cat')
'daxin is cat'
>>>
Python自帶的模闆功能極其有限,如果我們想要在模闆中使用控制語句,和表達式,以及繼承等功能的話,就無法實作了。
目前主流的模闆系統,最常用的就是jinja2和mako
jinja2介紹
jinja2是Flask作者開發的一個模闆系統,起初是仿django模闆的一個模闆引擎,為Flask提供模闆支援,由于其靈活,快速和安全等優點被廣泛使用。
jinja2的優點
jinja2之是以被廣泛使用是因為它具有以下優點:
1.相對于Template,jinja2更加靈活,它提供了控制結構,表達式和繼承等。
2.相對于Mako,jinja2僅有控制結構,不允許在模闆中編寫太多的業務邏輯。
3.相對于Django模闆,jinja2性能更好。
4.Jinja2模闆的可讀性很棒。
安裝jinja2
由于jinja2屬于第三方子產品,首先需要對其進行安裝
pip3 install jinja2
測試模闆是否安裝成功
python -c "import jinja2"
# 沒有報錯就表示安裝成功
# 必須用雙引号"
jinja2文法
作為一個模闆系統,它還提供了特殊的文法,我們按照它支援的文法進行編寫之後,就能使用jinja2子產品進行渲染。
基本文法
在jinja2中,存在三種文法:
1.控制結構 {% %}
2.變量取值 {{ }}
3.注釋 {# #}
下面是一個簡單的jinja2例子
{# This is jinja code
{% for file in filenames %}
...
{% endfor %}
#}
可以看到,for循環的使用方式和Python比較類似,但是沒有了句尾的冒号,另外需要使用endfor最為結尾,其實在jinja2中,if也是一樣的,結尾需要使用endif。
jinja2變量
jinja2模闆中使用 {{ }} 文法表示一個變量,它是一種特殊的占位符。當利用jinja2進行渲染的時候,它會把這些特殊的占位符進行填充/替換,jinja2支援python中所有的Python資料類型比如清單、字段、對象等。
<p>this is a dicectory:{{ mydict['key'] }} </p>
<p>this is a list:{{ mylist[3] }} </p>
<p>this is a object:{{ myobject.something() }} </p>
jinja2中的過濾器
變量可以通過“過濾器”進行修改,過濾器可以了解為是jinja2裡面的内置函數和字元串處理函數。
常用的過濾器有:
那麼如何使用這些過濾器呢? 隻需要在變量後面使用管道(|)分割,多個過濾器可以鍊式調用,前一個過濾器的輸出會作為後一個過濾器的輸入。
{{ 'abc' | captialize }}
# Abc
{{ 'abc' | upper }}
# ABC
{{ 'hello world' | title }}
# Hello World
{{ "hello world" | replace('world','daxin') | upper }}
# HELLO DAXIN
{{ 18.18 | round | int }}
# 18
jinja2的控制結構
jinja2中的if語句類似與Python的if語句,它也具有單分支,多分支等多種結構,不同的是,條件語句不需要使用冒号結尾,而結束控制語句,需要使用endif關鍵字。
{% if daxin.safe %}
daxin is safe.
{% elif daxin.dead %}
daxin is dead
{% else %}
daxin is okay
{% endif %}
jinja2的for循環
jinja2中的for循環用于疊代Python的資料類型,包括清單,元組和字典。在jinja2中不存在while循環。
疊代清單
<ul>
{% for user in users %}
<li>{{ user.username|title }}</li>
{% endfor %}
</ul>
疊代字典
<dl>
{% for key, value in my_dict.iteritems() %}
<dt>{{ key }}</dt>
<dd>{{ value}}</dd>
{% endfor %}
</dl>
當然也可以加入else語句,在循環正确執行完畢後,執行
在for循環中,jinja2還提供了一些特殊的變量,用以來擷取目前的周遊狀态:
jinja2的宏
宏類似于Python中的函數,我們在宏中定義行為,還可以進行傳遞參數,就像Python中的函數一樣一樣兒的。
在宏中定義一個宏的關鍵字是macro,後面跟其 宏的名稱和參數等
{% macro input(name,age=18) %} # 參數age的預設值為18
<input type='text' name="{{ name }}" value="{{ age }}" >
{% endmacro %}
調用方法也和Python的類似
<p>{{ input('daxin') }} </p>
<p>{{ input('daxin',age=20) }} </p>
jinja2的繼承和Super函數
jinja2中最強大的部分就是模闆繼承。模闆繼承允許我們建立一個基本(骨架)檔案,其他檔案從該骨架檔案繼承,然後針對自己需要的地方進行修改。
jinja2的骨架檔案中,利用block關鍵字表示其包涵的内容可以進行修改。
以下面的骨架檔案base.html為例:
<!DOCTYPE html>
<html >
<head>
{% block head %}
<link rel="stylesheet" href="style.css" target="_blank" rel="external nofollow" />
<title>{% block title %}{% endblock %} - My Webpage</title>
{% endblock %}
</head>
<body>
<div id="content">{% block content %}{% endblock %}</div>
<div id="footer">
{% block footer %}
<script>This is javascript code </script>
{% endblock %}
</div>
</body>
</html>
這裡定義了四處 block,即:head,title,content,footer。那怎麼進行繼承和變量替換呢?注意看下面的檔案
{% extend "base.html" %} # 繼承base.html檔案
{% block title %} Dachenzi {% endblock %} # 定制title部分的内容
{% block head %}
{{ super() }} # 用于擷取原有的資訊
<style type='text/css'>
.important { color: #FFFFFF }
</style>
{% endblock %}
# 其他不修改的原封不同的繼承
PS: super()函數 表示擷取block塊中定義的原來的内容。
利用jinja2進行渲染
jinja2子產品中有一個名為Enviroment的類,這個類的執行個體用于存儲配置和全局對象,然後從檔案系統或其他位置中加載模闆。
基本使用方法
大多數應用都在初始化的時候撞見一個Environment對象,并用它加載模闆。Environment支援兩種加載方式:
PackageLoader:包加載器
FileSystemLoader:檔案系統加載器
PackageLoader
使用包加載器來加載文檔的最簡單的方式如下
from jinja2 import PackageLoader,Environment
env = Environment(loader=PackageLoader('python_project','templates')) # 建立一個包加載器對象
template = env.get_template('bast.html') # 擷取一個模闆檔案
template.render(name='daxin',age=18) # 渲染
其中:
PackageLoader()的兩個參數為:python包的名稱,以及模闆目錄名稱。
get_template():擷取模闆目錄下的某個具體檔案。
render():接受變量,對模闆進行渲染
FileSystemLoader
檔案系統加載器,不需要模闆檔案存在某個Python包下,可以直接通路系統中的檔案。
所有巧合的是要麼是上天注定要麼是一個人偷偷的在努力。
個人微信公衆号,專注于學習資源、筆記分享,歡迎關注。我們一起成長,一起學習。一直純真着,善良着,溫情地熱愛生活,,如果覺得有點用的話,請不要吝啬你手中點贊的權力,謝謝我親愛的讀者朋友。
Desire is the starting point of all achievement, not a hope, not a wish, but a keen pulsating desire which transcends everything.
渴望是所有成就的原點,不是希望、不是願望,而是一個熱切、令人悸動、淩駕一切的渴望。
2020年4月2日于重慶城口
好好學習,天天向上,終有所獲