annotate genshi/template/eval.py @ 1024:a5e09a7ba12d trunk

Add support for kwonlyargs and kw_defaults attributes of AST argument nodes.
author hodgestar
date Sun, 16 Feb 2014 19:36:21 +0000
parents 2036193f89e7
children
rev   line source
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
1 # -*- coding: utf-8 -*-
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
2 #
897
64f04a2c5e66 Update changelog and copyright years.
cmlenz
parents: 896
diff changeset
3 # Copyright (C) 2006-2010 Edgewall Software
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
4 # All rights reserved.
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
5 #
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
6 # This software is licensed as described in the file COPYING, which
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
7 # you should have received as part of this distribution. The terms
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
8 # are also available at http://genshi.edgewall.org/wiki/License.
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
9 #
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
10 # This software consists of voluntary contributions made by many
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
11 # individuals. For the exact contribution history, see the revision
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
12 # history and logs, available at http://genshi.edgewall.org/log/.
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
13
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
14 """Support for "safe" evaluation of Python expressions."""
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
15
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
16 import __builtin__
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
17
601
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
18 from textwrap import dedent
793
be88c77839fc Get rid of a couple more -3 warnings.
cmlenz
parents: 750
diff changeset
19 from types import CodeType
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
20
401
68772732c896 Make the `Markup` class available by default in template expressions. Closes #67.
cmlenz
parents: 396
diff changeset
21 from genshi.core import Markup
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
22 from genshi.template.astutil import ASTTransformer, ASTCodeGenerator, \
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
23 _ast, parse
418
c478a6fa9e77 Make expression error handling more strict. Closes #88.
cmlenz
parents: 408
diff changeset
24 from genshi.template.base import TemplateRuntimeError
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
25 from genshi.util import flatten
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
26
1023
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
27 from genshi.compat import get_code_params, build_code_chunk, isstring, \
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
28 IS_PYTHON2
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
29
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
30 __all__ = ['Code', 'Expression', 'Suite', 'LenientLookup', 'StrictLookup',
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
31 'Undefined', 'UndefinedError']
425
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
32 __docformat__ = 'restructuredtext en'
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
33
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
34
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
35 # Check for a Python 2.4 bug in the eval loop
739
6de290dec976 Another Python 2.3 fix in the wake of #221.
cmlenz
parents: 736
diff changeset
36 has_star_import_bug = False
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
37 try:
736
a1e8b24bc1bb Yet another followup fix for #221.
cmlenz
parents: 733
diff changeset
38 class _FakeMapping(object):
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
39 __getitem__ = __setitem__ = lambda *a: None
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
40 exec 'from sys import *' in {}, _FakeMapping()
739
6de290dec976 Another Python 2.3 fix in the wake of #221.
cmlenz
parents: 736
diff changeset
41 except SystemError:
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
42 has_star_import_bug = True
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
43 del _FakeMapping
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
44
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
45
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
46 def _star_import_patch(mapping, modname):
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
47 """This function is used as helper if a Python version with a broken
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
48 star-import opcode is in use.
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
49 """
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
50 module = __import__(modname, None, None, ['__all__'])
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
51 if hasattr(module, '__all__'):
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
52 members = module.__all__
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
53 else:
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
54 members = [x for x in module.__dict__ if not x.startswith('_')]
733
43147cbc9ea3 Update to r855 for Python 2.3 support. Fixes #221 (hopefully).
athomas
parents: 731
diff changeset
55 mapping.update([(name, getattr(module, name)) for name in members])
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
56
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
57
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
58 class Code(object):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
59 """Abstract base class for the `Expression` and `Suite` classes."""
565
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
60 __slots__ = ['source', 'code', 'ast', '_globals']
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
61
606
37ff75bb4301 Changed the default error handling mode to "strict".
cmlenz
parents: 604
diff changeset
62 def __init__(self, source, filename=None, lineno=-1, lookup='strict',
604
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
63 xform=None):
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
64 """Create the code object, either from a string, or from an AST node.
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
65
425
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
66 :param source: either a string containing the source code, or an AST
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
67 node
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
68 :param filename: the (preferably absolute) name of the file containing
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
69 the code
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
70 :param lineno: the number of the line on which the code was found
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
71 :param lookup: the lookup class that defines how variables are looked
606
37ff75bb4301 Changed the default error handling mode to "strict".
cmlenz
parents: 604
diff changeset
72 up in the context; can be either "strict" (the default),
37ff75bb4301 Changed the default error handling mode to "strict".
cmlenz
parents: 604
diff changeset
73 "lenient", or a custom lookup class
604
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
74 :param xform: the AST transformer that should be applied to the code;
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
75 if `None`, the appropriate transformation is chosen
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
76 depending on the mode
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
77 """
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
78 if isinstance(source, basestring):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
79 self.source = source
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
80 node = _parse(source, mode=self.mode)
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
81 else:
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
82 assert isinstance(source, _ast.AST), \
601
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
83 'Expected string or AST node, but got %r' % source
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
84 self.source = '?'
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
85 if self.mode == 'eval':
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
86 node = _ast.Expression()
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
87 node.body = source
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
88 else:
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
89 node = _ast.Module()
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
90 node.body = [source]
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
91
565
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
92 self.ast = node
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
93 self.code = _compile(node, self.source, mode=self.mode,
604
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
94 filename=filename, lineno=lineno, xform=xform)
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
95 if lookup is None:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
96 lookup = LenientLookup
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
97 elif isinstance(lookup, basestring):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
98 lookup = {'lenient': LenientLookup, 'strict': StrictLookup}[lookup]
654
23b5138fd835 Fix thread-safety problem in template code evaluation. Closes #158. Thanks to Christian Boos for the patch.
cmlenz
parents: 606
diff changeset
99 self._globals = lookup.globals
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
100
715
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
101 def __getstate__(self):
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
102 state = {'source': self.source, 'ast': self.ast,
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
103 'lookup': self._globals.im_self}
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
104 state['code'] = get_code_params(self.code)
715
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
105 return state
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
106
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
107 def __setstate__(self, state):
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
108 self.source = state['source']
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
109 self.ast = state['ast']
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
110 self.code = CodeType(0, *state['code'])
715
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
111 self._globals = state['lookup'].globals
b5bd8c109209 Enable pickling of `Template` and `Code` objects.
cmlenz
parents: 702
diff changeset
112
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
113 def __eq__(self, other):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
114 return (type(other) == type(self)) and (self.code == other.code)
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
115
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
116 def __hash__(self):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
117 return hash(self.code)
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
118
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
119 def __ne__(self, other):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
120 return not self == other
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
121
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
122 def __repr__(self):
860
16d55698006a A bit of cleanup of the `Markup` Python implementation.
cmlenz
parents: 854
diff changeset
123 return '%s(%r)' % (type(self).__name__, self.source)
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
124
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
125
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
126 class Expression(Code):
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
127 """Evaluates Python expressions used in templates.
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
128
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
129 >>> data = dict(test='Foo', items=[1, 2, 3], dict={'some': 'thing'})
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
130 >>> Expression('test').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
131 'Foo'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
132
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
133 >>> Expression('items[0]').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
134 1
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
135 >>> Expression('items[-1]').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
136 3
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
137 >>> Expression('dict["some"]').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
138 'thing'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
139
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
140 Similar to e.g. Javascript, expressions in templates can use the dot
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
141 notation for attribute access to access items in mappings:
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
142
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
143 >>> Expression('dict.some').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
144 'thing'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
145
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
146 This also works the other way around: item access can be used to access
425
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
147 any object attribute:
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
148
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
149 >>> class MyClass(object):
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
150 ... myattr = 'Bar'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
151 >>> data = dict(mine=MyClass(), key='myattr')
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
152 >>> Expression('mine.myattr').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
153 'Bar'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
154 >>> Expression('mine["myattr"]').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
155 'Bar'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
156 >>> Expression('mine[key]').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
157 'Bar'
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
158
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
159 All of the standard Python operators are available to template expressions.
425
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
160 Built-in functions such as ``len()`` are also available in template
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
161 expressions:
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
162
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
163 >>> data = dict(items=[1, 2, 3])
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
164 >>> Expression('len(items)').evaluate(data)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
165 3
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
166 """
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
167 __slots__ = []
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
168 mode = 'eval'
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
169
343
35189e960252 Remove automatic calling of expression evaluation results if they are callable. See [http://groups.google.com/group/genshi/browse_thread/thread/f515986760918d41 this mailing list thread].
cmlenz
parents: 340
diff changeset
170 def evaluate(self, data):
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
171 """Evaluate the expression against the given data dictionary.
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
172
425
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
173 :param data: a mapping containing the data to evaluate against
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
174 :return: the result of the evaluation
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
175 """
418
c478a6fa9e77 Make expression error handling more strict. Closes #88.
cmlenz
parents: 408
diff changeset
176 __traceback_hide__ = 'before_and_this'
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
177 _globals = self._globals(data)
682
0653f6c1ffdf Assigning to a variable named `data` in a Python code block no longer breaks context lookup. We now use the name `__data__` for internal data, hoping that that name is not as commonly used in templates.
cmlenz
parents: 654
diff changeset
178 return eval(self.code, _globals, {'__data__': data})
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
179
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
180
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
181 class Suite(Code):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
182 """Executes Python statements used in templates.
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
183
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
184 >>> data = dict(test='Foo', items=[1, 2, 3], dict={'some': 'thing'})
473
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
185 >>> Suite("foo = dict['some']").execute(data)
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
186 >>> data['foo']
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
187 'thing'
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
188 """
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
189 __slots__ = []
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
190 mode = 'exec'
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
191
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
192 def execute(self, data):
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
193 """Execute the suite in the given data dictionary.
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
194
425
073640758a42 Try to use proper reStructuredText for docstrings throughout.
cmlenz
parents: 418
diff changeset
195 :param data: a mapping containing the data to execute in
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
196 """
418
c478a6fa9e77 Make expression error handling more strict. Closes #88.
cmlenz
parents: 408
diff changeset
197 __traceback_hide__ = 'before_and_this'
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
198 _globals = self._globals(data)
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
199 exec self.code in _globals, data
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
200
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
201
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
202 UNDEFINED = object()
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
203
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
204
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
205 class UndefinedError(TemplateRuntimeError):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
206 """Exception thrown when a template expression attempts to access a variable
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
207 not defined in the context.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
208
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
209 :see: `LenientLookup`, `StrictLookup`
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
210 """
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
211 def __init__(self, name, owner=UNDEFINED):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
212 if owner is not UNDEFINED:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
213 message = '%s has no member named "%s"' % (repr(owner), name)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
214 else:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
215 message = '"%s" not defined' % name
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
216 TemplateRuntimeError.__init__(self, message)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
217
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
218
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
219 class Undefined(object):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
220 """Represents a reference to an undefined variable.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
221
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
222 Unlike the Python runtime, template expressions can refer to an undefined
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
223 variable without causing a `NameError` to be raised. The result will be an
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
224 instance of the `Undefined` class, which is treated the same as ``False`` in
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
225 conditions, but raise an exception on any other operation:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
226
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
227 >>> foo = Undefined('foo')
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
228 >>> bool(foo)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
229 False
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
230 >>> list(foo)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
231 []
853
f33ecf3c319e Convert a bunch of print statements to py3k compatible syntax.
cmlenz
parents: 845
diff changeset
232 >>> print(foo)
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
233 undefined
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
234
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
235 However, calling an undefined variable, or trying to access an attribute
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
236 of that variable, will raise an exception that includes the name used to
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
237 reference that undefined variable.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
238
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
239 >>> try:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
240 ... foo('bar')
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
241 ... except UndefinedError, e:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
242 ... print e.msg
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
243 "foo" not defined
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
244
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
245 >>> try:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
246 ... foo.bar
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
247 ... except UndefinedError, e:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
248 ... print e.msg
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
249 "foo" not defined
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
250
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
251 :see: `LenientLookup`
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
252 """
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
253 __slots__ = ['_name', '_owner']
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
254
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
255 def __init__(self, name, owner=UNDEFINED):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
256 """Initialize the object.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
257
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
258 :param name: the name of the reference
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
259 :param owner: the owning object, if the variable is accessed as a member
418
c478a6fa9e77 Make expression error handling more strict. Closes #88.
cmlenz
parents: 408
diff changeset
260 """
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
261 self._name = name
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
262 self._owner = owner
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
263
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
264 def __iter__(self):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
265 return iter([])
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
266
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
267 def __nonzero__(self):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
268 return False
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
269
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
270 def __repr__(self):
860
16d55698006a A bit of cleanup of the `Markup` Python implementation.
cmlenz
parents: 854
diff changeset
271 return '<%s %r>' % (type(self).__name__, self._name)
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
272
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
273 def __str__(self):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
274 return 'undefined'
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
275
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
276 def _die(self, *args, **kwargs):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
277 """Raise an `UndefinedError`."""
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
278 __traceback_hide__ = True
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
279 raise UndefinedError(self._name, self._owner)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
280 __call__ = __getattr__ = __getitem__ = _die
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
281
878
c8cac1b264e4 Apply patch from #324 for Python 2.6.2 compatibility fix.
cmlenz
parents: 860
diff changeset
282 # Hack around some behavior introduced in Python 2.6.2
c8cac1b264e4 Apply patch from #324 for Python 2.6.2 compatibility fix.
cmlenz
parents: 860
diff changeset
283 # http://genshi.edgewall.org/ticket/324
c8cac1b264e4 Apply patch from #324 for Python 2.6.2 compatibility fix.
cmlenz
parents: 860
diff changeset
284 __length_hint__ = None
c8cac1b264e4 Apply patch from #324 for Python 2.6.2 compatibility fix.
cmlenz
parents: 860
diff changeset
285
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
286
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
287 class LookupBase(object):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
288 """Abstract base class for variable lookup implementations."""
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
289
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
290 @classmethod
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
291 def globals(cls, data):
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
292 """Construct the globals dictionary to use as the execution context for
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
293 the expression or suite.
418
c478a6fa9e77 Make expression error handling more strict. Closes #88.
cmlenz
parents: 408
diff changeset
294 """
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
295 return {
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
296 '__data__': data,
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
297 '_lookup_name': cls.lookup_name,
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
298 '_lookup_attr': cls.lookup_attr,
579
2f7f6b70d5b9 Fix for augmented assignments to local variables. Thanks to Erik Bray for reporting the problem.
cmlenz
parents: 569
diff changeset
299 '_lookup_item': cls.lookup_item,
731
01bdf155db95 Workaround for a Python 2.4 bug that broke star imports in template code blocks. Closes #221. Many thanks to Armin Ronacher for the patch.
cmlenz
parents: 719
diff changeset
300 '_star_import_patch': _star_import_patch,
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
301 'UndefinedError': UndefinedError,
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
302 }
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
303
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
304 @classmethod
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
305 def lookup_name(cls, data, name):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
306 __traceback_hide__ = True
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
307 val = data.get(name, UNDEFINED)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
308 if val is UNDEFINED:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
309 val = BUILTINS.get(name, val)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
310 if val is UNDEFINED:
569
c17342ef9efb Attribute access in template expressions no longer silently ignores exceptions other than `AttributeError` raised in the attribute accessor.
cmlenz
parents: 568
diff changeset
311 val = cls.undefined(name)
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
312 return val
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
313
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
314 @classmethod
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
315 def lookup_attr(cls, obj, key):
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
316 __traceback_hide__ = True
702
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
317 try:
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
318 val = getattr(obj, key)
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
319 except AttributeError:
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
320 if hasattr(obj.__class__, key):
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
321 raise
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
322 else:
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
323 try:
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
324 val = obj[key]
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
325 except (KeyError, TypeError):
e5b0d9d6b406 Improve error reporting when accessing an attribute in a Python expression raises an `AttributeError`. Closes #191. Thanks to Michele Cella for the patch!
cmlenz
parents: 691
diff changeset
326 val = cls.undefined(key, owner=obj)
569
c17342ef9efb Attribute access in template expressions no longer silently ignores exceptions other than `AttributeError` raised in the attribute accessor.
cmlenz
parents: 568
diff changeset
327 return val
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
328
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
329 @classmethod
691
2298d798513e Minor cleanup in eval module.
cmlenz
parents: 684
diff changeset
330 def lookup_item(cls, obj, key):
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
331 __traceback_hide__ = True
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
332 if len(key) == 1:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
333 key = key[0]
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
334 try:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
335 return obj[key]
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
336 except (AttributeError, KeyError, IndexError, TypeError), e:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
337 if isinstance(key, basestring):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
338 val = getattr(obj, key, UNDEFINED)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
339 if val is UNDEFINED:
569
c17342ef9efb Attribute access in template expressions no longer silently ignores exceptions other than `AttributeError` raised in the attribute accessor.
cmlenz
parents: 568
diff changeset
340 val = cls.undefined(key, owner=obj)
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
341 return val
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
342 raise
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
343
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
344 @classmethod
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
345 def undefined(cls, key, owner=UNDEFINED):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
346 """Can be overridden by subclasses to specify behavior when undefined
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
347 variables are accessed.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
348
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
349 :param key: the name of the variable
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
350 :param owner: the owning object, if the variable is accessed as a member
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
351 """
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
352 raise NotImplementedError
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
353
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
354
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
355 class LenientLookup(LookupBase):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
356 """Default variable lookup mechanism for expressions.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
357
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
358 When an undefined variable is referenced using this lookup style, the
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
359 reference evaluates to an instance of the `Undefined` class:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
360
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
361 >>> expr = Expression('nothing', lookup='lenient')
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
362 >>> undef = expr.evaluate({})
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
363 >>> undef
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
364 <Undefined 'nothing'>
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
365
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
366 The same will happen when a non-existing attribute or item is accessed on
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
367 an existing object:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
368
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
369 >>> expr = Expression('something.nil', lookup='lenient')
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
370 >>> expr.evaluate({'something': dict()})
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
371 <Undefined 'nil'>
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
372
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
373 See the documentation of the `Undefined` class for details on the behavior
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
374 of such objects.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
375
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
376 :see: `StrictLookup`
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
377 """
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
378
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
379 @classmethod
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
380 def undefined(cls, key, owner=UNDEFINED):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
381 """Return an ``Undefined`` object."""
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
382 __traceback_hide__ = True
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
383 return Undefined(key, owner=owner)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
384
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
385
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
386 class StrictLookup(LookupBase):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
387 """Strict variable lookup mechanism for expressions.
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
388
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
389 Referencing an undefined variable using this lookup style will immediately
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
390 raise an ``UndefinedError``:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
391
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
392 >>> expr = Expression('nothing', lookup='strict')
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
393 >>> try:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
394 ... expr.evaluate({})
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
395 ... except UndefinedError, e:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
396 ... print e.msg
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
397 "nothing" not defined
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
398
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
399 The same happens when a non-existing attribute or item is accessed on an
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
400 existing object:
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
401
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
402 >>> expr = Expression('something.nil', lookup='strict')
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
403 >>> try:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
404 ... expr.evaluate({'something': dict()})
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
405 ... except UndefinedError, e:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
406 ... print e.msg
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
407 {} has no member named "nil"
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
408 """
822
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
409
70fddd2262f5 Get rid of some Python 2.3 legacy that's no longer needed now that 2.4 is the baseline.
cmlenz
parents: 806
diff changeset
410 @classmethod
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
411 def undefined(cls, key, owner=UNDEFINED):
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
412 """Raise an ``UndefinedError`` immediately."""
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
413 __traceback_hide__ = True
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
414 raise UndefinedError(key, owner=owner)
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
415
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
416
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
417 def _parse(source, mode='eval'):
601
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
418 source = source.strip()
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
419 if mode == 'exec':
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
420 lines = [line.expandtabs() for line in source.splitlines()]
716
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
421 if lines:
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
422 first = lines[0]
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
423 rest = dedent('\n'.join(lines[1:])).rstrip()
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
424 if first.rstrip().endswith(':') and not rest[0].isspace():
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
425 rest = '\n'.join([' %s' % line for line in rest.splitlines()])
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
426 source = '\n'.join([first, rest])
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
427 if isinstance(source, unicode):
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
428 source = (u'\ufeff' + source).encode('utf-8')
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
429 return parse(source, mode)
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
430
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
431
604
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
432 def _compile(node, source=None, mode='eval', filename=None, lineno=-1,
416e46209da1 Fix bug that slipped into [717]: the code of a `py:with` directive was not being compiled with AST transformations applied.
cmlenz
parents: 601
diff changeset
433 xform=None):
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
434 if not filename:
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
435 filename = '<string>'
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
436 if IS_PYTHON2:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
437 # Python 2 requires non-unicode filenames
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
438 if isinstance(filename, unicode):
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
439 filename = filename.encode('utf-8', 'replace')
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
440 else:
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
441 # Python 3 requires unicode filenames
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
442 if not isinstance(filename, unicode):
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
443 filename = filename.decode('utf-8', 'replace')
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
444 if lineno <= 0:
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
445 lineno = 1
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
446
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
447 if xform is None:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
448 xform = {
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
449 'eval': ExpressionASTTransformer
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
450 }.get(mode, TemplateASTTransformer)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
451 tree = xform().visit(node)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
452
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
453 if mode == 'eval':
601
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
454 name = '<Expression %r>' % (source or '?')
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
455 else:
601
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
456 lines = source.splitlines()
716
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
457 if not lines:
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
458 extract = ''
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
459 else:
eee7483041dd fix ticket [209] - make sure py:with is valid, and add a test to make sure empty py:for is invalid
aflett
parents: 715
diff changeset
460 extract = lines[0]
601
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
461 if len(lines) > 1:
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
462 extract += ' ...'
59fbd7586454 Simplify implementation of `py:with` directive by compiling to a `Suite`, instead of manually breaking up the statement and compiling each part to an `Expression`. Also, the first line of code in a `Suite` is now stored as the "function name" of the bytecode, so that it shows up in tracebacks.
cmlenz
parents: 586
diff changeset
463 name = '<Suite %r>' % (extract)
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
464 new_source = ASTCodeGenerator(tree).code
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
465 code = compile(new_source, filename, mode)
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
466
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
467 try:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
468 # We'd like to just set co_firstlineno, but it's readonly. So we need
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
469 # to clone the code object while adjusting the line number
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
470 return build_code_chunk(code, filename, name, lineno)
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
471 except RuntimeError:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
472 return code
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
473
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
474
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
475 def _new(class_, *args, **kwargs):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
476 ret = class_()
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
477 for attr, value in zip(ret._fields, args):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
478 if attr in kwargs:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
479 raise ValueError('Field set both in args and kwargs')
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
480 setattr(ret, attr, value)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
481 for attr, value in kwargs:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
482 setattr(ret, attr, value)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
483 return ret
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
484
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
485
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
486 BUILTINS = __builtin__.__dict__.copy()
442
97544725bb7f Back out [510] and instead implement configurable error handling modes. The default is the old 0.3.x behaviour, but more strict error handling is available as an option.
cmlenz
parents: 438
diff changeset
487 BUILTINS.update({'Markup': Markup, 'Undefined': Undefined})
563
9d1c5c290254 Built-in Python constants (such as `None`) in expressions are used directly instead of being looked up from the context.
cmlenz
parents: 473
diff changeset
488 CONSTANTS = frozenset(['False', 'True', 'None', 'NotImplemented', 'Ellipsis'])
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
489
564
aeb89e9730df Alias `__contains__` to `has_key` in `Context` class for code outside of Genshi that may expect that for some wild reason.
cmlenz
parents: 563
diff changeset
490
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
491 class TemplateASTTransformer(ASTTransformer):
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
492 """Concrete AST transformer that implements the AST transformations needed
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
493 for code embedded in templates.
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
494 """
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
495
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
496 def __init__(self):
586
3670ea49c65a Fixes for nonlocal variable access in code blocks, as well as nested function and class definitions.
cmlenz
parents: 582
diff changeset
497 self.locals = [CONSTANTS]
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
498
1023
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
499 def _process(self, names, node):
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
500 if not IS_PYTHON2 and isinstance(node, _ast.arg):
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
501 names.add(node.arg)
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
502 elif isstring(node):
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
503 names.add(node)
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
504 elif isinstance(node, _ast.Name):
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
505 names.add(node.id)
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
506 elif isinstance(node, _ast.alias):
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
507 names.add(node.asname or node.name)
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
508 elif isinstance(node, _ast.Tuple):
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
509 for elt in node.elts:
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
510 self._process(names, elt)
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
511
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
512 def _extract_names(self, node):
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
513 names = set()
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
514 if hasattr(node, 'args'):
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
515 for arg in node.args:
1023
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
516 self._process(names, arg)
1024
a5e09a7ba12d Add support for kwonlyargs and kw_defaults attributes of AST argument nodes.
hodgestar
parents: 1023
diff changeset
517 if hasattr(node, 'kwonlyargs'):
a5e09a7ba12d Add support for kwonlyargs and kw_defaults attributes of AST argument nodes.
hodgestar
parents: 1023
diff changeset
518 for arg in node.kwonlyargs:
a5e09a7ba12d Add support for kwonlyargs and kw_defaults attributes of AST argument nodes.
hodgestar
parents: 1023
diff changeset
519 self._process(names, arg)
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
520 if hasattr(node, 'vararg'):
1023
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
521 self._process(names, node.vararg)
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
522 if hasattr(node, 'kwarg'):
1023
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
523 self._process(names, node.kwarg)
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
524 elif hasattr(node, 'names'):
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
525 for elt in node.names:
1023
2036193f89e7 Add support for Python 3.4 AST (support for NameConstants and changes to existing to arguments node attributes).
hodgestar
parents: 934
diff changeset
526 self._process(names, elt)
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
527 return names
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
528
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
529 def visit_Str(self, node):
934
31bbb6f9e87b Merge r1142 from py3k:
hodgestar
parents: 897
diff changeset
530 if not isinstance(node.s, unicode):
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
531 try: # If the string is ASCII, return a `str` object
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
532 node.s.decode('ascii')
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
533 except ValueError: # Otherwise return a `unicode` object
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
534 return _new(_ast.Str, node.s.decode('utf-8'))
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
535 return node
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
536
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
537 def visit_ClassDef(self, node):
586
3670ea49c65a Fixes for nonlocal variable access in code blocks, as well as nested function and class definitions.
cmlenz
parents: 582
diff changeset
538 if len(self.locals) > 1:
3670ea49c65a Fixes for nonlocal variable access in code blocks, as well as nested function and class definitions.
cmlenz
parents: 582
diff changeset
539 self.locals[-1].add(node.name)
405
5340931530e2 Support for Python code blocks using the `<?python ?>` processing instruction. Closes #84.
cmlenz
parents: 401
diff changeset
540 self.locals.append(set())
565
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
541 try:
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
542 return ASTTransformer.visit_ClassDef(self, node)
565
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
543 finally:
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
544 self.locals.pop()
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
545
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
546 def visit_Import(self, node):
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
547 if len(self.locals) > 1:
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
548 self.locals[-1].update(self._extract_names(node))
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
549 return ASTTransformer.visit_Import(self, node)
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
550
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
551 def visit_ImportFrom(self, node):
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
552 if [a.name for a in node.names] == ['*']:
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
553 if has_star_import_bug:
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
554 # This is a Python 2.4 bug. Only if we have a broken Python
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
555 # version do we need to apply this hack
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
556 node = _new(_ast.Expr, _new(_ast.Call,
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
557 _new(_ast.Name, '_star_import_patch'), [
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
558 _new(_ast.Name, '__data__'),
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
559 _new(_ast.Str, node.module)
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
560 ], (), ()))
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
561 return node
806
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
562 if len(self.locals) > 1:
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
563 self.locals[-1].update(self._extract_names(node))
c66c83861266 Fix for import statements in function defs in template code blocks (#276).
cmlenz
parents: 803
diff changeset
564 return ASTTransformer.visit_ImportFrom(self, node)
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
565
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
566 def visit_FunctionDef(self, node):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
567 if len(self.locals) > 1:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
568 self.locals[-1].add(node.name)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
569
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
570 self.locals.append(self._extract_names(node.args))
565
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
571 try:
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
572 return ASTTransformer.visit_FunctionDef(self, node)
565
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
573 finally:
53b37e4f2921 * The I18n extractor now handles gettext function calls that use non-string parameters as well as keyword arguments.
cmlenz
parents: 564
diff changeset
574 self.locals.pop()
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
575
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
576 # GeneratorExp(expr elt, comprehension* generators)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
577 def visit_GeneratorExp(self, node):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
578 gens = []
845
4ec4377f49ee Fix nested list comprehensions & generator expressions (fixes #327)
mgood
parents: 822
diff changeset
579 for generator in node.generators:
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
580 # comprehension = (expr target, expr iter, expr* ifs)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
581 self.locals.append(set())
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
582 gen = _new(_ast.comprehension, self.visit(generator.target),
845
4ec4377f49ee Fix nested list comprehensions & generator expressions (fixes #327)
mgood
parents: 822
diff changeset
583 self.visit(generator.iter),
4ec4377f49ee Fix nested list comprehensions & generator expressions (fixes #327)
mgood
parents: 822
diff changeset
584 [self.visit(if_) for if_ in generator.ifs])
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
585 gens.append(gen)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
586
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
587 # use node.__class__ to make it reusable as ListComp
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
588 ret = _new(node.__class__, self.visit(node.elt), gens)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
589 #delete inserted locals
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
590 del self.locals[-len(node.generators):]
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
591 return ret
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
592
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
593 # ListComp(expr elt, comprehension* generators)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
594 visit_ListComp = visit_GeneratorExp
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
595
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
596 def visit_Lambda(self, node):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
597 self.locals.append(self._extract_names(node.args))
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
598 try:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
599 return ASTTransformer.visit_Lambda(self, node)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
600 finally:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
601 self.locals.pop()
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
602
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
603 def visit_Name(self, node):
357
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
604 # If the name refers to a local inside a lambda, list comprehension, or
62de137b9322 Improve the way locals (in list comprehensions, lambdas and generator expressions) are handled in template expressions.
cmlenz
parents: 343
diff changeset
605 # generator expression, leave it alone
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
606 if isinstance(node.ctx, _ast.Load) and \
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
607 node.id not in flatten(self.locals):
586
3670ea49c65a Fixes for nonlocal variable access in code blocks, as well as nested function and class definitions.
cmlenz
parents: 582
diff changeset
608 # Otherwise, translate the name ref into a context lookup
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
609 name = _new(_ast.Name, '_lookup_name', _ast.Load())
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
610 namearg = _new(_ast.Name, '__data__', _ast.Load())
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
611 strarg = _new(_ast.Str, node.id)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
612 node = _new(_ast.Call, name, [namearg, strarg], [])
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
613 elif isinstance(node.ctx, _ast.Store):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
614 if len(self.locals) > 1:
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
615 self.locals[-1].add(node.id)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
616
586
3670ea49c65a Fixes for nonlocal variable access in code blocks, as well as nested function and class definitions.
cmlenz
parents: 582
diff changeset
617 return node
336
7763f7aec949 Refactoring: `genshi.template` is now a package, it was getting way to crowded in that file.
cmlenz
parents:
diff changeset
618
473
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
619
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
620 class ExpressionASTTransformer(TemplateASTTransformer):
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
621 """Concrete AST transformer that implements the AST transformations needed
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
622 for code embedded in templates.
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
623 """
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
624
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
625 def visit_Attribute(self, node):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
626 if not isinstance(node.ctx, _ast.Load):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
627 return ASTTransformer.visit_Attribute(self, node)
473
4ed941aa0cbf Apply patch from #113, also closing #114.
cmlenz
parents: 442
diff changeset
628
794
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
629 func = _new(_ast.Name, '_lookup_attr', _ast.Load())
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
630 args = [self.visit(node.value), _new(_ast.Str, node.attr)]
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
631 return _new(_ast.Call, func, args, [])
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
632
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
633 def visit_Subscript(self, node):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
634 if not isinstance(node.ctx, _ast.Load) or \
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
635 not isinstance(node.slice, _ast.Index):
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
636 return ASTTransformer.visit_Subscript(self, node)
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
637
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
638 func = _new(_ast.Name, '_lookup_item', _ast.Load())
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
639 args = [
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
640 self.visit(node.value),
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
641 _new(_ast.Tuple, (self.visit(node.slice.value),), _ast.Load())
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
642 ]
f9e23d472a6e Merged AST branch back into trunk. Most of this code was written by Marcin Kurczych for his Google Summer of Code 2008 project. The merge of this branch means that Genshi now uses the native `_ast` module on Python >= 2.5, and an emulation thereof on Python 2.4. This replaces the usage of the `compiler` package, which was deprecated in Python 2.6 and removed in Python 3.0. Another effect is that Genshi now runs on Google AppEngine (although performance is bad due to the lack of template caching).
cmlenz
parents: 793
diff changeset
643 return _new(_ast.Call, func, args, [])
Copyright (C) 2012-2017 Edgewall Software