kuroの覚え書き

96の個人的覚え書き

business logicとpresentation logic

データベースとのやり取り、ユーザーからのリクエスト受付などのタスクとブラウザへの表示タスクを分けておかないとメンテナンスが大変。
Flaskでは後半の表示部分をJinja2というtemplate engineで処理している。
ここをもう一度ちゃんと押さえておく。

基本中の基本
template/
にhtmlファイルを置くとflaskアプリから参照される。
hello.py

from flask import Flask, render_template
from flask_script import Manager

app = Flask(__name__)

manager = Manager(app)
#flask_scriptを導入して拡張した部分

@app.route('/')
def index():
    return render_template('index.html')
#render_templateを使ってtemplate/index.htmlの中身を読み込む

@app.route('/user/<name>')
def user(name):
    return render_template('user.html', name=name)
#name=nameの左側のnameはtemplate(user.html)のなかでプレースホルダ({{}}の中身)として名付けられた引数としてのname。右側のnameはここで得られた変数としてのname。ああややこしい。別のなまえにしときゃいいのに。

if __name__ == '__main__':
    manager.run()
#managerを通して起動

index.html

<h1>Hello, World!</h1>

user.html

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

htmlファイルと言ってもヘッダーはなくてもいいようだ。titleタグとかはちゃんとそのまま使える。


if条件分岐の利用
user.htmlを

{% if name == 'hoge' %}
        <h2>Hello, {{ name }}!</h2>
{% else %}
        <h2>Hello, Stranger.</h2>
{% endif %}

とすると
http://127.0.0.1:5000/user/hoge
だと

Hello, hoge!


http://127.0.0.1:5000/user/hogehoge
だと

Hello, stranger.


となる。

forループの利用

from flask import Flask, render_template
from flask_script import Manager

app = Flask(__name__)

manager = Manager(app)

@app.route('/')
def index():
    return render_template('index.html', comments = ["test1", "test2", "test3"] )
if __name__ == '__main__':
    manager.run()

index.html

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

こういう組み合わせで

  • test1
  • test2
  • test3

と返ってくる

またマクロを使って コメントを読み取る部分とリストを作る部分を分けて

{% macro render_comment(comment) %}
        <li>{{comment}}</li>
{% endmacro %}

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

このように記述したり
更にmacroを別のファイルにしてインポートすることも
template/macros.html

{% macro render_comment(comment) %}
        <li>{{comment}}</li>
{% endmacro %}

index.html

{% import 'macros.html' as macros %}
<ul>
        {% for comment in comments %}
                {{ macros.render_comment(comment) }}
        {% endfor %}
</ul>

この場合macros.htmlに複数マクロを並べておいて流用できたりするわけだね。