Nic
Nic

Reputation: 3507

How to access the environment of jinja2.Template

When defining an environment including a loader, it is easy to add custom filters:

from jinja2 import Environment, PackageLoader, select_autoescape
env = Environment(
    loader=PackageLoader('tests', 'templates'),
    autoescape=select_autoescape(['html', 'xml'])
)
env.filters['rsttable'] = rsttable

But I struggle to add custom filters to a template created the Template() constructor:

from jinja2 import Template

def highlight(txt):
    return '**%s**' % txt

tpl = Template('hello {{name | highlight}}')
tpl.render(name='me')

yields:

TemplateAssertionError: no filter named 'highlight'

The Jinja2 doc is quite cryptic for me:

Template objects created from the constructor rather than an environment do have an environment attribute that points to a temporary environment that is probably shared with other templates created with the constructor and compatible settings.

Upvotes: 1

Views: 3258

Answers (1)

AKX
AKX

Reputation: 168834

If your template is an inline string, like in your example, use Environment.from_string() to acquire the template. (If it's a file, use .get_template().)

This way it'll have the filters registered with the environment wired up.

from jinja2 import Environment, PackageLoader, select_autoescape

env = Environment(
    loader=PackageLoader("tests", "templates"),
    autoescape=select_autoescape(["html", "xml"]),
)


def highlight(txt):
    return "**%s**" % txt


env.filters["highlight"] = highlight


tpl = env.from_string("hello {{name | highlight}}")
tpl.render(name="me")

Upvotes: 3

Related Questions