1 # -*- coding: utf-8 -*-
3 jinja2.testsuite.inheritance
4 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~
6 Tests the template inheritance feature.
8 :copyright: (c) 2010 by the Jinja Team.
9 :license: BSD, see LICENSE for more details.
13 from jinja2
.testsuite
import JinjaTestCase
15 from jinja2
import Environment
, DictLoader
19 |{% block block1 %}block 1 from layout{% endblock %}
20 |{% block block2 %}block 2 from layout{% endblock %}
22 {% block block4 %}nested block 4 from layout{% endblock %}
26 {% extends "layout" %}
27 {% block block1 %}block 1 from level1{% endblock %}'''
30 {% extends "level1" %}
31 {% block block2 %}{% block block5 %}nested block 5 from level2{%
32 endblock %}{% endblock %}'''
35 {% extends "level2" %}
36 {% block block5 %}block 5 from level3{% endblock %}
37 {% block block4 %}block 4 from level3{% endblock %}
41 {% extends "level3" %}
42 {% block block3 %}block 3 from level4{% endblock %}
45 WORKINGTEMPLATE
= '''\
46 {% extends "layout" %}
56 env
= Environment(loader
=DictLoader({
57 'layout': LAYOUTTEMPLATE
,
58 'level1': LEVEL1TEMPLATE
,
59 'level2': LEVEL2TEMPLATE
,
60 'level3': LEVEL3TEMPLATE
,
61 'level4': LEVEL4TEMPLATE
,
62 'working': WORKINGTEMPLATE
66 class InheritanceTestCase(JinjaTestCase
):
68 def test_layout(self
):
69 tmpl
= env
.get_template('layout')
70 assert tmpl
.render() == ('|block 1 from layout|block 2 from '
71 'layout|nested block 4 from layout|')
73 def test_level1(self
):
74 tmpl
= env
.get_template('level1')
75 assert tmpl
.render() == ('|block 1 from level1|block 2 from '
76 'layout|nested block 4 from layout|')
78 def test_level2(self
):
79 tmpl
= env
.get_template('level2')
80 assert tmpl
.render() == ('|block 1 from level1|nested block 5 from '
81 'level2|nested block 4 from layout|')
83 def test_level3(self
):
84 tmpl
= env
.get_template('level3')
85 assert tmpl
.render() == ('|block 1 from level1|block 5 from level3|'
86 'block 4 from level3|')
89 tmpl
= env
.get_template('level4')
90 assert tmpl
.render() == ('|block 1 from level1|block 5 from '
91 'level3|block 3 from level4|')
94 env
= Environment(loader
=DictLoader({
95 'a': '{% block intro %}INTRO{% endblock %}|'
96 'BEFORE|{% block data %}INNER{% endblock %}|AFTER',
97 'b': '{% extends "a" %}{% block data %}({{ '
98 'super() }}){% endblock %}',
99 'c': '{% extends "b" %}{% block intro %}--{{ '
100 'super() }}--{% endblock %}\n{% block data '
101 '%}[{{ super() }}]{% endblock %}'
103 tmpl
= env
.get_template('c')
104 assert tmpl
.render() == '--INTRO--|BEFORE|[(INNER)]|AFTER'
106 def test_working(self
):
107 tmpl
= env
.get_template('working')
109 def test_reuse_blocks(self
):
110 tmpl
= env
.from_string('{{ self.foo() }}|{% block foo %}42'
111 '{% endblock %}|{{ self.foo() }}')
112 assert tmpl
.render() == '42|42|42'
114 def test_preserve_blocks(self
):
115 env
= Environment(loader
=DictLoader({
116 'a': '{% if false %}{% block x %}A{% endblock %}{% endif %}{{ self.x() }}',
117 'b': '{% extends "a" %}{% block x %}B{{ super() }}{% endblock %}'
119 tmpl
= env
.get_template('b')
120 assert tmpl
.render() == 'BA'
122 def test_dynamic_inheritance(self
):
123 env
= Environment(loader
=DictLoader({
124 'master1': 'MASTER1{% block x %}{% endblock %}',
125 'master2': 'MASTER2{% block x %}{% endblock %}',
126 'child': '{% extends master %}{% block x %}CHILD{% endblock %}'
128 tmpl
= env
.get_template('child')
129 for m
in range(1, 3):
130 assert tmpl
.render(master
='master%d' % m
) == 'MASTER%dCHILD' % m
132 def test_multi_inheritance(self
):
133 env
= Environment(loader
=DictLoader({
134 'master1': 'MASTER1{% block x %}{% endblock %}',
135 'master2': 'MASTER2{% block x %}{% endblock %}',
136 'child': '''{% if master %}{% extends master %}{% else %}{% extends
137 'master1' %}{% endif %}{% block x %}CHILD{% endblock %}'''
139 tmpl
= env
.get_template('child')
140 assert tmpl
.render(master
='master2') == 'MASTER2CHILD'
141 assert tmpl
.render(master
='master1') == 'MASTER1CHILD'
142 assert tmpl
.render() == 'MASTER1CHILD'
144 def test_scoped_block(self
):
145 env
= Environment(loader
=DictLoader({
146 'master.html': '{% for item in seq %}[{% block item scoped %}'
147 '{% endblock %}]{% endfor %}'
149 t
= env
.from_string('{% extends "master.html" %}{% block item %}'
150 '{{ item }}{% endblock %}')
151 assert t
.render(seq
=range(5)) == '[0][1][2][3][4]'
153 def test_super_in_scoped_block(self
):
154 env
= Environment(loader
=DictLoader({
155 'master.html': '{% for item in seq %}[{% block item scoped %}'
156 '{{ item }}{% endblock %}]{% endfor %}'
158 t
= env
.from_string('{% extends "master.html" %}{% block item %}'
159 '{{ super() }}|{{ item * 2 }}{% endblock %}')
160 assert t
.render(seq
=range(5)) == '[0|0][1|2][2|4][3|6][4|8]'
162 def test_scoped_block_after_inheritance(self
):
163 env
= Environment(loader
=DictLoader({
165 {% block useless %}{% endblock %}
168 {%- extends 'layout.html' %}
169 {% from 'helpers.html' import foo with context %}
171 {% for x in [1, 2, 3] %}
172 {% block testing scoped %}
179 {% macro foo(x) %}{{ the_foo + x }}{% endmacro %}
182 rv
= env
.get_template('index.html').render(the_foo
=42).split()
183 assert rv
== ['43', '44', '45']
186 class BugFixTestCase(JinjaTestCase
):
188 def test_fixed_macro_scoping_bug(self
):
189 assert Environment(loader
=DictLoader({
191 {% extends 'details.html' %}
193 {% macro my_macro() %}
197 {% block inner_box %}
202 {% extends 'standard.html' %}
204 {% macro my_macro() %}
209 {% block outer_box %}
211 {% block inner_box %}
218 {% block content %} {% endblock %}
220 })).get_template("test.html").render().split() == [u
'outer_box', u
'my_macro']
224 suite
= unittest
.TestSuite()
225 suite
.addTest(unittest
.makeSuite(InheritanceTestCase
))
226 suite
.addTest(unittest
.makeSuite(BugFixTestCase
))