aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Lord <davidism@gmail.com>2020-03-30 11:40:59 -0700
committerDavid Lord <davidism@gmail.com>2020-03-30 11:40:59 -0700
commit0a370316c6a4f0d034da5f90df5a671a32a8e376 (patch)
treea291ea51000c3d9aa7d32776d96ce609b68473aa
parentc074fd5ecb7af70b2f864c9ef545fffd38dc203b (diff)
parent786867a47cdff625ebdab9fa1dbfe65a0c7e1924 (diff)
downloadjinja-0a370316c6a4f0d034da5f90df5a671a32a8e376.tar.gz
Merge branch '2.11.x'
-rw-r--r--CHANGES.rst4
-rw-r--r--src/jinja2/lexer.py8
-rw-r--r--src/jinja2/utils.py3
-rw-r--r--tests/test_async.py11
-rw-r--r--tests/test_lexnparse.py18
5 files changed, 41 insertions, 3 deletions
diff --git a/CHANGES.rst b/CHANGES.rst
index c2f51f56..580d411e 100644
--- a/CHANGES.rst
+++ b/CHANGES.rst
@@ -32,6 +32,10 @@ Unreleased
when using Pytest. Due to the difficulty in supporting Python 2 and
:pep:`451` simultaneously, the changes are reverted until 3.0.
:pr:`1182`
+- Fix line numbers in error messages when newlines are stripped.
+ :pr:`1178`
+- The special ``namespace()`` assignment object in templates works in
+ async environments. :issue:`1180`
Version 2.11.1
diff --git a/src/jinja2/lexer.py b/src/jinja2/lexer.py
index e0b7a2e9..fc44dbeb 100644
--- a/src/jinja2/lexer.py
+++ b/src/jinja2/lexer.py
@@ -636,6 +636,7 @@ class Lexer:
source_length = len(source)
balancing_stack = []
lstrip_unless_re = self.lstrip_unless_re
+ newlines_stripped = 0
while 1:
# tokenizer loop
@@ -672,7 +673,9 @@ class Lexer:
if strip_sign == "-":
# Strip all whitespace between the text and the tag.
- groups = (text.rstrip(),) + groups[1:]
+ stripped = text.rstrip()
+ newlines_stripped = text[len(stripped) :].count("\n")
+ groups = (stripped,) + groups[1:]
elif (
# Not marked for preserving whitespace.
strip_sign != "+"
@@ -712,7 +715,8 @@ class Lexer:
data = groups[idx]
if data or token not in ignore_if_empty:
yield lineno, token, data
- lineno += data.count("\n")
+ lineno += data.count("\n") + newlines_stripped
+ newlines_stripped = 0
# strings as token just are yielded as it.
else:
diff --git a/src/jinja2/utils.py b/src/jinja2/utils.py
index b373950e..8ee02958 100644
--- a/src/jinja2/utils.py
+++ b/src/jinja2/utils.py
@@ -643,7 +643,8 @@ class Namespace:
self.__attrs = dict(*args, **kwargs)
def __getattribute__(self, name):
- if name == "_Namespace__attrs":
+ # __class__ is needed for the awaitable check in async mode
+ if name in {"_Namespace__attrs", "__class__"}:
return object.__getattribute__(self, name)
try:
return self.__attrs[name]
diff --git a/tests/test_async.py b/tests/test_async.py
index 45713d5d..bfdcdb21 100644
--- a/tests/test_async.py
+++ b/tests/test_async.py
@@ -577,3 +577,14 @@ class TestAsyncForLoop:
def test_awaitable_property_slicing(self, test_env_async):
t = test_env_async.from_string("{% for x in a.b[:1] %}{{ x }}{% endfor %}")
assert t.render(a=dict(b=[1, 2, 3])) == "1"
+
+
+def test_namespace_awaitable(test_env_async):
+ async def _test():
+ t = test_env_async.from_string(
+ '{% set ns = namespace(foo="Bar") %}{{ ns.foo }}'
+ )
+ actual = await t.render_async()
+ assert actual == "Bar"
+
+ run(_test())
diff --git a/tests/test_lexnparse.py b/tests/test_lexnparse.py
index d14a6ccb..60574169 100644
--- a/tests/test_lexnparse.py
+++ b/tests/test_lexnparse.py
@@ -163,6 +163,24 @@ class TestLexer:
else:
pytest.raises(TemplateSyntaxError, env.from_string, t)
+ def test_lineno_with_strip(self, env):
+ tokens = env.lex(
+ """\
+<html>
+ <body>
+ {%- block content -%}
+ <hr>
+ {{ item }}
+ {% endblock %}
+ </body>
+</html>"""
+ )
+ for tok in tokens:
+ lineno, token_type, value = tok
+ if token_type == "name" and value == "item":
+ assert lineno == 5
+ break
+
class TestParser:
def test_php_syntax(self, env):