web-dev-qa-db-ja.com

テンプレートコード内で変数の値を設定する方法は?

テンプレートがあるとします

<html>
<div>Hello {{name}}!</div>
</html>

テスト中に、このテンプレートを呼び出すpythonコードを変更せずに変数の値を定義すると便利です。だから私はこのようなものを探しています

{% set name="World" %}     
<html>
<div>Hello {{name}}!</div>
</html>

Djangoにはこのようなものがありますか?

182
Alexis

with テンプレートタグを使用できます。

{% with name="World" %}     
<html>
<div>Hello {{name}}!</div>
</html>
{% endwith %}
280
John

すべてを「with」ブロックに入れる必要のない別の方法は、コンテキストに新しい変数を追加するカスタムタグを作成することです。次のように:

class SetVarNode(template.Node):
    def __init__(self, new_val, var_name):
        self.new_val = new_val
        self.var_name = var_name
    def render(self, context):
        context[self.var_name] = self.new_val
        return ''

import re
@register.tag
def setvar(parser,token):
    # This version uses a regular expression to parse tag contents.
    try:
        # Splitting by None == splitting by spaces.
        tag_name, arg = token.contents.split(None, 1)
    except ValueError:
        raise template.TemplateSyntaxError, "%r tag requires arguments" % token.contents.split()[0]
    m = re.search(r'(.*?) as (\w+)', arg)
    if not m:
        raise template.TemplateSyntaxError, "%r tag had invalid arguments" % tag_name
    new_val, var_name = m.groups()
    if not (new_val[0] == new_val[-1] and new_val[0] in ('"', "'")):
        raise template.TemplateSyntaxError, "%r tag's argument should be in quotes" % tag_name
    return SetVarNode(new_val[1:-1], var_name)

これにより、テンプレートに次のようなものを書くことができます。

{% setvar "a string" as new_template_var %}

このほとんどは ここから引用 であったことに注意してください

29
Karim

テンプレートタグを作成します。

アプリには、models.pyviews.pyなどと同じレベルにtemplatetagsディレクトリが含まれている必要があります。これがまだ存在しない場合は、作成してください。__init__.pyファイルは、ディレクトリがPythonパッケージとして扱われるようにします。

次のコードを使用して、templatetagsディレクトリ内にdefine_action.pyという名前のファイルを作成します。

from Django import template
register = template.Library()

@register.assignment_tag
def define(val=None):
  return val

注:開発サーバーは自動的に再起動しません。 templatetagsモジュールを追加したら、テンプレートでタグまたはフィルターを使用する前にサーバーを再起動する必要があります。


次に、テンプレートで、次のようにコンテキストに値を割り当てることができます。

{% load define_action %}
{% if item %}

   {% define "Edit" as action %}

{% else %}

   {% define "Create" as action %}

{% endif %}


Would you like to {{action}} this item?
28
Mods Vs Rockers

ジョンが説明したようなトリックがあります。ただし、設計上のDjangoのテンプレート言語は、変数の設定をサポートしていません( テンプレートのDjangoドキュメント の「哲学」ボックスを参照してください)。
このため、任意の変数を変更する推奨方法は、Pythonコードをタッチすることでです。

21
rob

これに対する最善の解決策は、カスタムassignment_tagを記述することです。このソリューションは、withタグを使用するよりもクリーンです。ロジックとスタイリングを非常に明確に分離できるためです。

テンプレートタグファイル(appname/templatetags/hello_world.pyなど)を作成することから始めます。

from Django import template

register = template.Library()

@register.assignment_tag
def get_addressee():
    return "World"

これで、テンプレートでget_addresseeテンプレートタグを使用できます。

{% load hello_world %}

{% get_addressee as addressee %}

<html>
    <body>
        <h1>hello {{addressee}}</h1>
    </body>
</html>
10
unique entity

おそらく default template filter は2009年にはオプションではありませんでした...

<html>
<div>Hello {{name|default:"World"}}!</div>
</html>
4
John Mee

これは一般的には良い考えではありません。 pythonのすべてのロジックを実行し、表示するデータをテンプレートに渡します。テンプレートは、ロジックを心配するのではなく、デザインに携わる人がデザインに集中できるように、できるだけシンプルにする必要があります。

例を挙げると、テンプレート内で派生情報が必要な場合は、pythonコード内の変数に取得してから、テンプレートに渡すことをお勧めします。

3
Sarang

withステートメント を使用します。

{% with total=business.employees.count %}
    {{ total }} employee{{ total|pluralize }}
{% endwith %}

この回答 の最初の段落のコードを暗示することはできません。たぶん、テンプレート言語は古いフォーマットを非推奨にしていたでしょう。

2
ramwin

テンプレートでは次のようにできます:

{% jump_link as name %}
{% for obj in name %}
    <div>{{obj.helo}} - {{obj.how}}</div>
{% endfor %}

テンプレートタグには、次のようなタグを追加できます

@register.assignment_tag
def jump_link():
    listArr = []
    for i in range(5):
        listArr.append({"helo" : i,"how" : i})
    return listArr
1
Ashish Gupta