annotate Lib/ast.py @ 80661:94de77bd0b4b 2.7

Issue #16194: document imp.load_dynamic problems when read several extension modules from the same binary object file.
author Andrew Svetlov <andrew.svetlov@gmail.com>
date Thu, 29 Nov 2012 19:51:28 +0200
parents 93a41df8c737
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
1 # -*- coding: utf-8 -*-
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
2 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
3 ast
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
4 ~~~
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
5
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
6 The `ast` module helps Python applications to process trees of the Python
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
7 abstract syntax grammar. The abstract syntax itself might change with
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
8 each Python release; this module helps to find out programmatically what
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
9 the current grammar looks like and allows modifications of it.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
10
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
11 An abstract syntax tree can be generated by passing `ast.PyCF_ONLY_AST` as
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
12 a flag to the `compile()` builtin function or by using the `parse()`
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
13 function from this module. The result will be a tree of objects whose
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
14 classes all inherit from `ast.AST`.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
15
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
16 A modified abstract syntax tree can be compiled into a Python code object
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
17 using the built-in `compile()` function.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
18
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
19 Additionally various helper functions are provided that make working with
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
20 the trees simpler. The main intention of the helper functions and this
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
21 module in general is to provide an easy to use interface for libraries
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
22 that work tightly with the python syntax (template engines for example).
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
23
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
24
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
25 :copyright: Copyright 2008 by Armin Ronacher.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
26 :license: Python License.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
27 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
28 from _ast import *
49559
415137d0e20a Merged revisions 66984 via svnmerge from
Benjamin Peterson <benjamin@python.org>
parents: 47794
diff changeset
29 from _ast import __version__
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
30
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
31
67750
93a41df8c737 Issue #11000 ast.parse doc fix (r88172)
Terry Reedy <tjreedy@udel.edu>
parents: 67482
diff changeset
32 def parse(source, filename='<unknown>', mode='exec'):
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
33 """
67750
93a41df8c737 Issue #11000 ast.parse doc fix (r88172)
Terry Reedy <tjreedy@udel.edu>
parents: 67482
diff changeset
34 Parse the source into an AST node.
93a41df8c737 Issue #11000 ast.parse doc fix (r88172)
Terry Reedy <tjreedy@udel.edu>
parents: 67482
diff changeset
35 Equivalent to compile(source, filename, mode, PyCF_ONLY_AST).
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
36 """
67750
93a41df8c737 Issue #11000 ast.parse doc fix (r88172)
Terry Reedy <tjreedy@udel.edu>
parents: 67482
diff changeset
37 return compile(source, filename, mode, PyCF_ONLY_AST)
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
38
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
39
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
40 def literal_eval(node_or_string):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
41 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
42 Safely evaluate an expression node or a string containing a Python
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
43 expression. The string or node provided may only consist of the following
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
44 Python literal structures: strings, numbers, tuples, lists, dicts, booleans,
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
45 and None.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
46 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
47 _safe_names = {'None': None, 'True': True, 'False': False}
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
48 if isinstance(node_or_string, basestring):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
49 node_or_string = parse(node_or_string, mode='eval')
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
50 if isinstance(node_or_string, Expression):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
51 node_or_string = node_or_string.body
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
52 def _convert(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
53 if isinstance(node, Str):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
54 return node.s
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
55 elif isinstance(node, Num):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
56 return node.n
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
57 elif isinstance(node, Tuple):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
58 return tuple(map(_convert, node.elts))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
59 elif isinstance(node, List):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
60 return list(map(_convert, node.elts))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
61 elif isinstance(node, Dict):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
62 return dict((_convert(k), _convert(v)) for k, v
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
63 in zip(node.keys, node.values))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
64 elif isinstance(node, Name):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
65 if node.id in _safe_names:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
66 return _safe_names[node.id]
50765
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
67 elif isinstance(node, BinOp) and \
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
68 isinstance(node.op, (Add, Sub)) and \
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
69 isinstance(node.right, Num) and \
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
70 isinstance(node.right.n, complex) and \
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
71 isinstance(node.left, Num) and \
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
72 isinstance(node.left.n, (int, long, float)):
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
73 left = node.left.n
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
74 right = node.right.n
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
75 if isinstance(node.op, Add):
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
76 return left + right
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
77 else:
c776b6d814c2 ast.literal_eval can properly evaluate complex numbers now. This fixes issue4907.
Armin Ronacher <armin.ronacher@active-4.com>
parents: 49559
diff changeset
78 return left - right
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
79 raise ValueError('malformed string')
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
80 return _convert(node_or_string)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
81
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
82
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
83 def dump(node, annotate_fields=True, include_attributes=False):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
84 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
85 Return a formatted dump of the tree in *node*. This is mainly useful for
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
86 debugging purposes. The returned string will show the names and the values
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
87 for fields. This makes the code impossible to evaluate, so if evaluation is
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
88 wanted *annotate_fields* must be set to False. Attributes such as line
47794
16b7c500b753 Docstring correction
Andrew M. Kuchling <amk@amk.ca>
parents: 47541
diff changeset
89 numbers and column offsets are not dumped by default. If this is wanted,
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
90 *include_attributes* can be set to True.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
91 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
92 def _format(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
93 if isinstance(node, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
94 fields = [(a, _format(b)) for a, b in iter_fields(node)]
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
95 rv = '%s(%s' % (node.__class__.__name__, ', '.join(
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
96 ('%s=%s' % field for field in fields)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
97 if annotate_fields else
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
98 (b for a, b in fields)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
99 ))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
100 if include_attributes and node._attributes:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
101 rv += fields and ', ' or ' '
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
102 rv += ', '.join('%s=%s' % (a, _format(getattr(node, a)))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
103 for a in node._attributes)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
104 return rv + ')'
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
105 elif isinstance(node, list):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
106 return '[%s]' % ', '.join(_format(x) for x in node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
107 return repr(node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
108 if not isinstance(node, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
109 raise TypeError('expected AST, got %r' % node.__class__.__name__)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
110 return _format(node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
111
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
112
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
113 def copy_location(new_node, old_node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
114 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
115 Copy source location (`lineno` and `col_offset` attributes) from
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
116 *old_node* to *new_node* if possible, and return *new_node*.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
117 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
118 for attr in 'lineno', 'col_offset':
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
119 if attr in old_node._attributes and attr in new_node._attributes \
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
120 and hasattr(old_node, attr):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
121 setattr(new_node, attr, getattr(old_node, attr))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
122 return new_node
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
123
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
124
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
125 def fix_missing_locations(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
126 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
127 When you compile a node tree with compile(), the compiler expects lineno and
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
128 col_offset attributes for every node that supports them. This is rather
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
129 tedious to fill in for generated nodes, so this helper adds these attributes
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
130 recursively where not already set, by setting them to the values of the
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
131 parent node. It works recursively starting at *node*.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
132 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
133 def _fix(node, lineno, col_offset):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
134 if 'lineno' in node._attributes:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
135 if not hasattr(node, 'lineno'):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
136 node.lineno = lineno
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
137 else:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
138 lineno = node.lineno
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
139 if 'col_offset' in node._attributes:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
140 if not hasattr(node, 'col_offset'):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
141 node.col_offset = col_offset
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
142 else:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
143 col_offset = node.col_offset
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
144 for child in iter_child_nodes(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
145 _fix(child, lineno, col_offset)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
146 _fix(node, 1, 0)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
147 return node
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
148
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
149
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
150 def increment_lineno(node, n=1):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
151 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
152 Increment the line number of each node in the tree starting at *node* by *n*.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
153 This is useful to "move code" to a different location in a file.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
154 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
155 for child in walk(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
156 if 'lineno' in child._attributes:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
157 child.lineno = getattr(child, 'lineno', 0) + n
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
158 return node
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
159
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
160
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
161 def iter_fields(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
162 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
163 Yield a tuple of ``(fieldname, value)`` for each field in ``node._fields``
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
164 that is present on *node*.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
165 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
166 for field in node._fields:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
167 try:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
168 yield field, getattr(node, field)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
169 except AttributeError:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
170 pass
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
171
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
172
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
173 def iter_child_nodes(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
174 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
175 Yield all direct child nodes of *node*, that is, all fields that are nodes
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
176 and all items of fields that are lists of nodes.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
177 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
178 for name, field in iter_fields(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
179 if isinstance(field, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
180 yield field
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
181 elif isinstance(field, list):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
182 for item in field:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
183 if isinstance(item, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
184 yield item
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
185
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
186
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
187 def get_docstring(node, clean=True):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
188 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
189 Return the docstring for the given node or None if no docstring can
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
190 be found. If the node provided does not have docstrings a TypeError
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
191 will be raised.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
192 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
193 if not isinstance(node, (FunctionDef, ClassDef, Module)):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
194 raise TypeError("%r can't have docstrings" % node.__class__.__name__)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
195 if node.body and isinstance(node.body[0], Expr) and \
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
196 isinstance(node.body[0].value, Str):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
197 if clean:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
198 import inspect
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
199 return inspect.cleandoc(node.body[0].value.s)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
200 return node.body[0].value.s
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
201
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
202
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
203 def walk(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
204 """
67482
7ec21653a4d1 Merged revisions 87876-87877 via svnmerge from
Georg Brandl <georg@python.org>
parents: 50765
diff changeset
205 Recursively yield all descendant nodes in the tree starting at *node*
7ec21653a4d1 Merged revisions 87876-87877 via svnmerge from
Georg Brandl <georg@python.org>
parents: 50765
diff changeset
206 (including *node* itself), in no specified order. This is useful if you
7ec21653a4d1 Merged revisions 87876-87877 via svnmerge from
Georg Brandl <georg@python.org>
parents: 50765
diff changeset
207 only want to modify nodes in place and don't care about the context.
47541
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
208 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
209 from collections import deque
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
210 todo = deque([node])
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
211 while todo:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
212 node = todo.popleft()
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
213 todo.extend(iter_child_nodes(node))
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
214 yield node
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
215
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
216
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
217 class NodeVisitor(object):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
218 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
219 A node visitor base class that walks the abstract syntax tree and calls a
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
220 visitor function for every node found. This function may return a value
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
221 which is forwarded by the `visit` method.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
222
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
223 This class is meant to be subclassed, with the subclass adding visitor
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
224 methods.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
225
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
226 Per default the visitor functions for the nodes are ``'visit_'`` +
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
227 class name of the node. So a `TryFinally` node visit function would
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
228 be `visit_TryFinally`. This behavior can be changed by overriding
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
229 the `visit` method. If no visitor function exists for a node
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
230 (return value `None`) the `generic_visit` visitor is used instead.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
231
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
232 Don't use the `NodeVisitor` if you want to apply changes to nodes during
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
233 traversing. For this a special visitor exists (`NodeTransformer`) that
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
234 allows modifications.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
235 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
236
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
237 def visit(self, node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
238 """Visit a node."""
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
239 method = 'visit_' + node.__class__.__name__
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
240 visitor = getattr(self, method, self.generic_visit)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
241 return visitor(node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
242
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
243 def generic_visit(self, node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
244 """Called if no explicit visitor function exists for a node."""
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
245 for field, value in iter_fields(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
246 if isinstance(value, list):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
247 for item in value:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
248 if isinstance(item, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
249 self.visit(item)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
250 elif isinstance(value, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
251 self.visit(value)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
252
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
253
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
254 class NodeTransformer(NodeVisitor):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
255 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
256 A :class:`NodeVisitor` subclass that walks the abstract syntax tree and
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
257 allows modification of nodes.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
258
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
259 The `NodeTransformer` will walk the AST and use the return value of the
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
260 visitor methods to replace or remove the old node. If the return value of
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
261 the visitor method is ``None``, the node will be removed from its location,
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
262 otherwise it is replaced with the return value. The return value may be the
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
263 original node in which case no replacement takes place.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
264
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
265 Here is an example transformer that rewrites all occurrences of name lookups
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
266 (``foo``) to ``data['foo']``::
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
267
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
268 class RewriteName(NodeTransformer):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
269
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
270 def visit_Name(self, node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
271 return copy_location(Subscript(
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
272 value=Name(id='data', ctx=Load()),
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
273 slice=Index(value=Str(s=node.id)),
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
274 ctx=node.ctx
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
275 ), node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
276
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
277 Keep in mind that if the node you're operating on has child nodes you must
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
278 either transform the child nodes yourself or call the :meth:`generic_visit`
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
279 method for the node first.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
280
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
281 For nodes that were part of a collection of statements (that applies to all
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
282 statement nodes), the visitor may also return a list of nodes rather than
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
283 just a single node.
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
284
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
285 Usually you use the transformer like this::
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
286
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
287 node = YourTransformer().visit(node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
288 """
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
289
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
290 def generic_visit(self, node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
291 for field, old_value in iter_fields(node):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
292 old_value = getattr(node, field, None)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
293 if isinstance(old_value, list):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
294 new_values = []
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
295 for value in old_value:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
296 if isinstance(value, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
297 value = self.visit(value)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
298 if value is None:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
299 continue
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
300 elif not isinstance(value, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
301 new_values.extend(value)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
302 continue
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
303 new_values.append(value)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
304 old_value[:] = new_values
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
305 elif isinstance(old_value, AST):
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
306 new_node = self.visit(old_value)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
307 if new_node is None:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
308 delattr(node, field)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
309 else:
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
310 setattr(node, field, new_node)
ed572d260fa7 Add the "ast" module, containing helpers to ease use of the "_ast" classes.
Georg Brandl <georg@python.org>
parents:
diff changeset
311 return node