關於jinja2 宏定義的小問題

使用flask的render_template(渲染HTML模板)創建一個簡單的web程序,代碼如下:

#coding:utf-8
from flask import  Flask
from flask import render_template

app=Flask(__name__)

@app.route('/')
def f():
    comments=['nihao','jing']
    return render_template('if.html',comments=comments)

if __name__=='__main__':
    app.run()
HTML模板if.html如下:

<ul>
    {% for comment in comments %}
        <li>{{ comment }}</li>
    {% endfor %}
</ul>
運行結果如圖:


接下來用宏定義重新寫HTML模板,宏定義forms.html如下:

{% macro t(comment) %}
     <li>{{comment}}</li>
{% endmacro %}
在另一模板t_if.html中引用該宏定義:

{% import 'forms.html' as forms %} <!--將forms導入,as後面的名字可以隨意定義-->
<ul>
{% for comment in comments %}
        {{forms.t(comment)}}  <!--引用其中的宏定義-->
{% endfor %}
</ul>
運行後與上面效果相同。

雖然程序可以工作,但不理解宏定義究竟如何工作的,比如

{% macro t(comment) %}
括號裏面的參數有何規定和要求,主程序中的comments是如何傳到模板的等等,但搜了一下,發現大部分都是互相copy,並無深入介紹,so,自己動手豐衣足食。


首先,先試驗一下將

{% macro t(comment) %}
括號去掉,因爲受到c裏面define的影響,直覺上覺得用一個字母t代替下面的語句沒問題,試驗以後發現報錯,


看來缺了括號不行,那就加上括號,改爲:

{% macro t() %} 注意此時括號沒有參數
運行結果如下:

雖然沒報錯,但列表裏的內容顯示不出來了。我們分析,既然有兩個點,說明執行到了t_if.html中

{{forms.t()}}
這一步,只不過沒有內容沒顯示出來罷了。於是猜測
% macro t(comment) %}
括號中的comment是用來傳參的,再將t_if.html的
{% for comment in comments %}
        {{forms.t(comment)}}  <!--引用其中的宏定義-->
{% endfor %}

改爲

{% for c in comments %}
        {{forms.t(c)}}  <!--引用其中的宏定義-->
{% endfor %}
相應的forms.html也改爲
{% macro t(c) %}
     <li>{{c}}</li>
{% endmacro %}

可正常運行。

於是我們得出結論,jinja2 中的宏定義不能隨便定義,如果裏面有可變參數,需要用小括號將參數傳遞進去。



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章