Mercurial > repos > shellac > sam_consensus_v3
comparison env/lib/python3.9/site-packages/jinja2/nativetypes.py @ 0:4f3585e2f14b draft default tip
"planemo upload commit 60cee0fc7c0cda8592644e1aad72851dec82c959"
author | shellac |
---|---|
date | Mon, 22 Mar 2021 18:12:50 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:4f3585e2f14b |
---|---|
1 from ast import literal_eval | |
2 from itertools import chain | |
3 from itertools import islice | |
4 | |
5 from . import nodes | |
6 from ._compat import text_type | |
7 from .compiler import CodeGenerator | |
8 from .compiler import has_safe_repr | |
9 from .environment import Environment | |
10 from .environment import Template | |
11 | |
12 | |
13 def native_concat(nodes): | |
14 """Return a native Python type from the list of compiled nodes. If | |
15 the result is a single node, its value is returned. Otherwise, the | |
16 nodes are concatenated as strings. If the result can be parsed with | |
17 :func:`ast.literal_eval`, the parsed value is returned. Otherwise, | |
18 the string is returned. | |
19 | |
20 :param nodes: Iterable of nodes to concatenate. | |
21 """ | |
22 head = list(islice(nodes, 2)) | |
23 | |
24 if not head: | |
25 return None | |
26 | |
27 if len(head) == 1: | |
28 raw = head[0] | |
29 else: | |
30 raw = u"".join([text_type(v) for v in chain(head, nodes)]) | |
31 | |
32 try: | |
33 return literal_eval(raw) | |
34 except (ValueError, SyntaxError, MemoryError): | |
35 return raw | |
36 | |
37 | |
38 class NativeCodeGenerator(CodeGenerator): | |
39 """A code generator which renders Python types by not adding | |
40 ``to_string()`` around output nodes. | |
41 """ | |
42 | |
43 @staticmethod | |
44 def _default_finalize(value): | |
45 return value | |
46 | |
47 def _output_const_repr(self, group): | |
48 return repr(u"".join([text_type(v) for v in group])) | |
49 | |
50 def _output_child_to_const(self, node, frame, finalize): | |
51 const = node.as_const(frame.eval_ctx) | |
52 | |
53 if not has_safe_repr(const): | |
54 raise nodes.Impossible() | |
55 | |
56 if isinstance(node, nodes.TemplateData): | |
57 return const | |
58 | |
59 return finalize.const(const) | |
60 | |
61 def _output_child_pre(self, node, frame, finalize): | |
62 if finalize.src is not None: | |
63 self.write(finalize.src) | |
64 | |
65 def _output_child_post(self, node, frame, finalize): | |
66 if finalize.src is not None: | |
67 self.write(")") | |
68 | |
69 | |
70 class NativeEnvironment(Environment): | |
71 """An environment that renders templates to native Python types.""" | |
72 | |
73 code_generator_class = NativeCodeGenerator | |
74 | |
75 | |
76 class NativeTemplate(Template): | |
77 environment_class = NativeEnvironment | |
78 | |
79 def render(self, *args, **kwargs): | |
80 """Render the template to produce a native Python type. If the | |
81 result is a single node, its value is returned. Otherwise, the | |
82 nodes are concatenated as strings. If the result can be parsed | |
83 with :func:`ast.literal_eval`, the parsed value is returned. | |
84 Otherwise, the string is returned. | |
85 """ | |
86 vars = dict(*args, **kwargs) | |
87 | |
88 try: | |
89 return native_concat(self.root_render_func(self.new_context(vars))) | |
90 except Exception: | |
91 return self.environment.handle_exception() | |
92 | |
93 | |
94 NativeEnvironment.template_class = NativeTemplate |