ファイルシステムから直接jinjaテンプレートをロードする方法


87

pocoo.orgの神社のAPIドキュメントの状態:

アプリケーションのテンプレートをロードするようにJinja2を構成する最も簡単な方法は、おおよそ次のようになります。
from jinja2 import Environment, PackageLoader
env = Environment(loader=PackageLoader('yourapplication', 'templates'))
これにより、デフォルト設定のテンプレート環境と、アプリケーションpythonパッケージ内のtemplatesフォルダーでテンプレートを検索するローダーが作成されます。

結局のところ、これはそれほど単純ではありません。テンプレートを含むpythonパッケージを作成/インストールする必要があるため、特にコードを配布する意図がない場合は、不必要に複雑になります。ここここでこのトピックに関するSOの質問を参照できますが、答えはあいまいで満足のいくものではありません。

ナイーブな初心者がやりたいことは、明らかに、パッケージ内のリソースとしてではなく、ファイルシステムから直接テンプレートをロードすることです。 これはどのように行われますか?

回答:


129

方法は次のとおりです。のFileSystemLoader代わりにを使用しPackageLoaderます。私はここここでウェブ上例を見つけまし。テンプレートと同じディレクトリにPythonファイルがあるとしましょう。

./index.py
./template.html

このindex.pyはテンプレートを見つけてレンダリングします:

#!/usr/bin/python
import jinja2

templateLoader = jinja2.FileSystemLoader(searchpath="./")
templateEnv = jinja2.Environment(loader=templateLoader)
TEMPLATE_FILE = "template.html"
template = templateEnv.get_template(TEMPLATE_FILE)
outputText = template.render()  # this is where to put args to the template renderer

print(outputText)

結局のところ、jinja2 APIドキュメントには、すべての組み込みローダーについて説明するセクションがあるため、すぐに気付かなかったのは恥ずかしいことです。しかし、導入部はPackageLoader、デフォルトの「最も単純な」方法であるように思われるように表現されています。Pythonの初心者にとって、これは野生のガチョウの追跡につながる可能性があります。


96
1行でファイルからテンプレートをロードできないなんてばかげている例jinja2.load_template('template.html')
Matt

4
私は常にラッパーを持っており、アプリケーションでJinja2と呼んで、この冗長性をすべて入れて、次のように呼んでいます。Jinja2.render(template_name, data)
Seraf19年

11
重要なセキュリティリスク!あなたはほぼ確実に電話したいと思うでしょうjinja2.Environment(loader=templateLoader, autoescape=True)。または、詳細についてはAPIドキュメントを参照してください。ただ、見つけた私は、この答え、次からの主要なXSSの脆弱性になってしまった:/
andrewdotn

上部の両方のリンクが壊れています。
sshow

77

より簡単な方法は、jinj2.Templateコンストラクターを直接呼び出し、を使用openしてファイルをロードすることです。

from jinja2 import Template
with open('template.html.jinja2') as file_:
    template = Template(file_.read())
template.render(name='John')

1
残念ながら、これではカスタムフィルターを設定できません。カスタムフィルターがまだ存在しないため、テンプレートの読み込み中に初期化中にエラーが発生します。このようにして、初期化後にのみ環境にアクセスできます(フィルターを含めるため)。
ローナンPaixão

18

これが1つのライナーです:

template = Template(open('template_file.j2').read())

次に、テンプレートを別の行にレンダリングすることも、すべてを1行にレンダリングすることもできます。

rendered = Template(open('template_file.j2').read()).render(var="TEXT")

1
残念ながら、テンプレートの継承がある場合、Jinjaは参照されているテンプレートを見つけることができないため、これは機能しなくなります。
Bemmu

4
しかし、幸いなことに、継承を使用しない場合、これは単純で十分であり、たとえば単純な電子メールを送信したくないだけです。:)
smido 2010年

5

Python3.4 +とJinja2-v2.11 +を使用している場合、PythonのpathlibとFilesystemを組み合わせてフローを簡素化できます

from pathlib import Path
...

p = Path(__file__).parent.parent / 'templates' # sample relative path
env = Environment(
    loader=FileSystemLoader(Path(p)))
template = env.get_template('your_file.jinja2')

Template(file)Jinjaのテンプレート継承処理がうまく機能しない可能性があるため、直接使用することに慣れていません。

Pathlibのサポートは、最新バージョンのJinja(v2.11 +)でのみ追加されます。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.