blob: a44f8f551c5e0a25f5a10496c55500dd9e682060 [file] [log] [blame]
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001import ast
Victor Stinnere5fbe0c2020-09-15 18:03:34 +02002import builtins
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01003import dis
Ethan Furmana02cb472021-04-21 10:20:44 -07004import enum
Benjamin Peterson832bfe22011-08-09 16:15:04 -05005import os
6import sys
Victor Stinnere5fbe0c2020-09-15 18:03:34 +02007import types
Benjamin Peterson832bfe22011-08-09 16:15:04 -05008import unittest
Serhiy Storchakac3ea41e2019-08-26 10:13:19 +03009import warnings
Benjamin Peterson9ed37432012-07-08 11:13:36 -070010import weakref
Ivan Levkivskyi9932a222019-01-22 11:18:22 +000011from textwrap import dedent
Benjamin Peterson9ed37432012-07-08 11:13:36 -070012
13from test import support
Tim Peters400cbc32006-02-28 18:44:41 +000014
15def to_tuple(t):
Guido van Rossum3172c5d2007-10-16 18:12:55 +000016 if t is None or isinstance(t, (str, int, complex)):
Tim Peters400cbc32006-02-28 18:44:41 +000017 return t
18 elif isinstance(t, list):
19 return [to_tuple(e) for e in t]
20 result = [t.__class__.__name__]
Martin v. Löwis49c5da12006-03-01 22:49:05 +000021 if hasattr(t, 'lineno') and hasattr(t, 'col_offset'):
22 result.append((t.lineno, t.col_offset))
Serhiy Storchaka850a8852020-01-10 10:12:55 +020023 if hasattr(t, 'end_lineno') and hasattr(t, 'end_col_offset'):
24 result[-1] += (t.end_lineno, t.end_col_offset)
Tim Peters400cbc32006-02-28 18:44:41 +000025 if t._fields is None:
26 return tuple(result)
27 for f in t._fields:
28 result.append(to_tuple(getattr(t, f)))
29 return tuple(result)
30
Neal Norwitzee9b10a2008-03-31 05:29:39 +000031
Tim Peters400cbc32006-02-28 18:44:41 +000032# These tests are compiled through "exec"
Ezio Melotti85a86292013-08-17 16:57:41 +030033# There should be at least one test per statement
Tim Peters400cbc32006-02-28 18:44:41 +000034exec_tests = [
Benjamin Peterson6ccfe852011-06-27 17:46:06 -050035 # None
36 "None",
INADA Naokicb41b272017-02-23 00:31:59 +090037 # Module docstring
38 "'module docstring'",
Tim Peters400cbc32006-02-28 18:44:41 +000039 # FunctionDef
40 "def f(): pass",
INADA Naokicb41b272017-02-23 00:31:59 +090041 # FunctionDef with docstring
42 "def f(): 'function docstring'",
Benjamin Peterson6ccfe852011-06-27 17:46:06 -050043 # FunctionDef with arg
44 "def f(a): pass",
45 # FunctionDef with arg and default value
46 "def f(a=0): pass",
47 # FunctionDef with varargs
48 "def f(*args): pass",
49 # FunctionDef with kwargs
50 "def f(**kwargs): pass",
INADA Naokicb41b272017-02-23 00:31:59 +090051 # FunctionDef with all kind of args and docstring
52 "def f(a, b=1, c=None, d=[], e={}, *args, f=42, **kwargs): 'doc for f()'",
Tim Peters400cbc32006-02-28 18:44:41 +000053 # ClassDef
54 "class C:pass",
INADA Naokicb41b272017-02-23 00:31:59 +090055 # ClassDef with docstring
56 "class C: 'docstring for class C'",
Benjamin Peterson6ccfe852011-06-27 17:46:06 -050057 # ClassDef, new style class
58 "class C(object): pass",
Tim Peters400cbc32006-02-28 18:44:41 +000059 # Return
60 "def f():return 1",
61 # Delete
62 "del v",
63 # Assign
64 "v = 1",
Serhiy Storchakab619b092018-11-27 09:40:29 +020065 "a,b = c",
66 "(a,b) = c",
67 "[a,b] = c",
Tim Peters400cbc32006-02-28 18:44:41 +000068 # AugAssign
69 "v += 1",
Tim Peters400cbc32006-02-28 18:44:41 +000070 # For
71 "for v in v:pass",
72 # While
73 "while v:pass",
74 # If
75 "if v:pass",
Lysandros Nikolaou025a6022019-12-12 22:40:21 +010076 # If-Elif
77 "if a:\n pass\nelif b:\n pass",
Lysandros Nikolaou5936a4c2019-12-14 11:24:57 +010078 # If-Elif-Else
79 "if a:\n pass\nelif b:\n pass\nelse:\n pass",
Benjamin Petersonaeabd5f2011-05-27 15:02:03 -050080 # With
81 "with x as y: pass",
82 "with x as y, z as q: pass",
Tim Peters400cbc32006-02-28 18:44:41 +000083 # Raise
Collin Winter828f04a2007-08-31 00:04:24 +000084 "raise Exception('string')",
Tim Peters400cbc32006-02-28 18:44:41 +000085 # TryExcept
86 "try:\n pass\nexcept Exception:\n pass",
87 # TryFinally
88 "try:\n pass\nfinally:\n pass",
89 # Assert
90 "assert v",
91 # Import
92 "import sys",
93 # ImportFrom
94 "from sys import v",
Tim Peters400cbc32006-02-28 18:44:41 +000095 # Global
96 "global v",
97 # Expr
98 "1",
99 # Pass,
100 "pass",
101 # Break
Yury Selivanovb3d53132015-09-01 16:10:49 -0400102 "for v in v:break",
Tim Peters400cbc32006-02-28 18:44:41 +0000103 # Continue
Yury Selivanovb3d53132015-09-01 16:10:49 -0400104 "for v in v:continue",
Benjamin Peterson2e4b0e12009-09-11 22:36:20 +0000105 # for statements with naked tuples (see http://bugs.python.org/issue6704)
106 "for a,b in c: pass",
Serhiy Storchakab619b092018-11-27 09:40:29 +0200107 "for (a,b) in c: pass",
108 "for [a,b] in c: pass",
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500109 # Multiline generator expression (test for .lineno & .col_offset)
110 """(
111 (
112 Aa
113 ,
114 Bb
115 )
116 for
117 Aa
118 ,
119 Bb in Cc
120 )""",
121 # dictcomp
122 "{a : b for w in x for m in p if g}",
123 # dictcomp with naked tuple
124 "{a : b for v,w in x}",
125 # setcomp
126 "{r for l in x if g}",
127 # setcomp with naked tuple
128 "{r for l,m in x}",
Yury Selivanov75445082015-05-11 22:57:16 -0400129 # AsyncFunctionDef
INADA Naokicb41b272017-02-23 00:31:59 +0900130 "async def f():\n 'async function'\n await something()",
Yury Selivanov75445082015-05-11 22:57:16 -0400131 # AsyncFor
132 "async def f():\n async for e in i: 1\n else: 2",
133 # AsyncWith
134 "async def f():\n async with a as b: 1",
Yury Selivanovb3d53132015-09-01 16:10:49 -0400135 # PEP 448: Additional Unpacking Generalizations
136 "{**{1:2}, 2:3}",
137 "{*{1, 2}, 3}",
Yury Selivanov52c4e7c2016-09-09 10:36:01 -0700138 # Asynchronous comprehensions
139 "async def f():\n [i async for b in c]",
Serhiy Storchaka95b6acf2018-10-30 13:16:02 +0200140 # Decorated FunctionDef
Serhiy Storchaka26ae9f62019-10-26 16:46:05 +0300141 "@deco1\n@deco2()\n@deco3(1)\ndef f(): pass",
Serhiy Storchaka95b6acf2018-10-30 13:16:02 +0200142 # Decorated AsyncFunctionDef
Serhiy Storchaka26ae9f62019-10-26 16:46:05 +0300143 "@deco1\n@deco2()\n@deco3(1)\nasync def f(): pass",
Serhiy Storchaka95b6acf2018-10-30 13:16:02 +0200144 # Decorated ClassDef
Serhiy Storchaka26ae9f62019-10-26 16:46:05 +0300145 "@deco1\n@deco2()\n@deco3(1)\nclass C: pass",
Serhiy Storchakab619b092018-11-27 09:40:29 +0200146 # Decorator with generator argument
147 "@deco(a for a in b)\ndef f(): pass",
Lysandros Nikolaoud2e10982020-02-08 00:36:32 +0100148 # Decorator with attribute
149 "@a.b.c\ndef f(): pass",
Pablo Galindo0c9258a2019-03-18 13:51:53 +0000150 # Simple assignment expression
151 "(a := 1)",
Pablo Galindo2f58a842019-05-31 14:09:49 +0100152 # Positional-only arguments
153 "def f(a, /,): pass",
154 "def f(a, /, c, d, e): pass",
155 "def f(a, /, c, *, d, e): pass",
156 "def f(a, /, c, *, d, e, **kwargs): pass",
157 # Positional-only arguments with defaults
158 "def f(a=1, /,): pass",
159 "def f(a=1, /, b=2, c=4): pass",
160 "def f(a=1, /, b=2, *, c=4): pass",
161 "def f(a=1, /, b=2, *, c): pass",
162 "def f(a=1, /, b=2, *, c=4, **kwargs): pass",
163 "def f(a=1, /, b=2, *, c, **kwargs): pass",
Pablo Galindo0c9258a2019-03-18 13:51:53 +0000164
Tim Peters400cbc32006-02-28 18:44:41 +0000165]
166
167# These are compiled through "single"
168# because of overlap with "eval", it just tests what
169# can't be tested with "eval"
170single_tests = [
171 "1+2"
172]
173
174# These are compiled through "eval"
175# It should test all expressions
176eval_tests = [
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500177 # None
178 "None",
Tim Peters400cbc32006-02-28 18:44:41 +0000179 # BoolOp
180 "a and b",
181 # BinOp
182 "a + b",
183 # UnaryOp
184 "not v",
185 # Lambda
186 "lambda:None",
187 # Dict
188 "{ 1:2 }",
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500189 # Empty dict
190 "{}",
191 # Set
192 "{None,}",
193 # Multiline dict (test for .lineno & .col_offset)
194 """{
195 1
196 :
197 2
198 }""",
Tim Peters400cbc32006-02-28 18:44:41 +0000199 # ListComp
200 "[a for b in c if d]",
201 # GeneratorExp
202 "(a for b in c if d)",
Serhiy Storchakab619b092018-11-27 09:40:29 +0200203 # Comprehensions with multiple for targets
204 "[(a,b) for a,b in c]",
205 "[(a,b) for (a,b) in c]",
206 "[(a,b) for [a,b] in c]",
207 "{(a,b) for a,b in c}",
208 "{(a,b) for (a,b) in c}",
209 "{(a,b) for [a,b] in c}",
210 "((a,b) for a,b in c)",
211 "((a,b) for (a,b) in c)",
212 "((a,b) for [a,b] in c)",
Tim Peters400cbc32006-02-28 18:44:41 +0000213 # Yield - yield expressions can't work outside a function
214 #
215 # Compare
216 "1 < 2 < 3",
217 # Call
218 "f(1,2,c=3,*d,**e)",
Lysandros Nikolaou50d4f122019-12-18 01:20:55 +0100219 # Call with multi-character starred
220 "f(*[0, 1])",
Serhiy Storchakab619b092018-11-27 09:40:29 +0200221 # Call with a generator argument
222 "f(a for a in b)",
Tim Peters400cbc32006-02-28 18:44:41 +0000223 # Num
Guido van Rossume2a383d2007-01-15 16:59:06 +0000224 "10",
Tim Peters400cbc32006-02-28 18:44:41 +0000225 # Str
226 "'string'",
227 # Attribute
228 "a.b",
229 # Subscript
230 "a[b:c]",
231 # Name
232 "v",
233 # List
234 "[1,2,3]",
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500235 # Empty list
236 "[]",
Tim Peters400cbc32006-02-28 18:44:41 +0000237 # Tuple
Martin v. Löwis49c5da12006-03-01 22:49:05 +0000238 "1,2,3",
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500239 # Tuple
240 "(1,2,3)",
241 # Empty tuple
242 "()",
Martin v. Löwis49c5da12006-03-01 22:49:05 +0000243 # Combination
244 "a.b.c.d(a.b[1:2])",
245
Tim Peters400cbc32006-02-28 18:44:41 +0000246]
247
248# TODO: expr_context, slice, boolop, operator, unaryop, cmpop, comprehension
249# excepthandler, arguments, keywords, alias
250
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000251class AST_Tests(unittest.TestCase):
Tim Peters400cbc32006-02-28 18:44:41 +0000252
Batuhan TaĹźkaya397b96f2020-03-01 23:12:17 +0300253 def _is_ast_node(self, name, node):
254 if not isinstance(node, type):
255 return False
256 if "ast" not in node.__module__:
257 return False
258 return name != 'AST' and name[0].isupper()
259
Benjamin Peterson7a66fc22015-02-02 10:51:20 -0500260 def _assertTrueorder(self, ast_node, parent_pos):
Georg Brandl0c77a822008-06-10 16:37:50 +0000261 if not isinstance(ast_node, ast.AST) or ast_node._fields is None:
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000262 return
Georg Brandl0c77a822008-06-10 16:37:50 +0000263 if isinstance(ast_node, (ast.expr, ast.stmt, ast.excepthandler)):
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000264 node_pos = (ast_node.lineno, ast_node.col_offset)
Serhiy Storchaka95b6acf2018-10-30 13:16:02 +0200265 self.assertGreaterEqual(node_pos, parent_pos)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000266 parent_pos = (ast_node.lineno, ast_node.col_offset)
267 for name in ast_node._fields:
268 value = getattr(ast_node, name)
269 if isinstance(value, list):
Serhiy Storchaka95b6acf2018-10-30 13:16:02 +0200270 first_pos = parent_pos
271 if value and name == 'decorator_list':
272 first_pos = (value[0].lineno, value[0].col_offset)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000273 for child in value:
Serhiy Storchaka95b6acf2018-10-30 13:16:02 +0200274 self._assertTrueorder(child, first_pos)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000275 elif value is not None:
Benjamin Peterson7a66fc22015-02-02 10:51:20 -0500276 self._assertTrueorder(value, parent_pos)
Brandt Bucher145bf262021-02-26 14:51:55 -0800277 self.assertEqual(ast_node._fields, ast_node.__match_args__)
Tim Peters5ddfe412006-03-01 23:02:57 +0000278
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500279 def test_AST_objects(self):
280 x = ast.AST()
281 self.assertEqual(x._fields, ())
Benjamin Peterson7e0dbfb2012-03-12 09:46:44 -0700282 x.foobar = 42
283 self.assertEqual(x.foobar, 42)
284 self.assertEqual(x.__dict__["foobar"], 42)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500285
286 with self.assertRaises(AttributeError):
287 x.vararg
288
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500289 with self.assertRaises(TypeError):
Serhiy Storchakabace59d2020-03-22 20:33:34 +0200290 # "ast.AST constructor takes 0 positional arguments"
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500291 ast.AST(2)
292
Benjamin Peterson9ed37432012-07-08 11:13:36 -0700293 def test_AST_garbage_collection(self):
294 class X:
295 pass
296 a = ast.AST()
297 a.x = X()
298 a.x.a = a
299 ref = weakref.ref(a.x)
300 del a
301 support.gc_collect()
302 self.assertIsNone(ref())
303
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000304 def test_snippets(self):
305 for input, output, kind in ((exec_tests, exec_results, "exec"),
306 (single_tests, single_results, "single"),
307 (eval_tests, eval_results, "eval")):
308 for i, o in zip(input, output):
Yury Selivanovb3d53132015-09-01 16:10:49 -0400309 with self.subTest(action="parsing", input=i):
310 ast_tree = compile(i, "?", kind, ast.PyCF_ONLY_AST)
311 self.assertEqual(to_tuple(ast_tree), o)
312 self._assertTrueorder(ast_tree, (0, 0))
Victor Stinner15a30952016-02-08 22:45:06 +0100313 with self.subTest(action="compiling", input=i, kind=kind):
314 compile(ast_tree, "?", kind)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000315
Pablo Galindo0c9258a2019-03-18 13:51:53 +0000316 def test_ast_validation(self):
317 # compile() is the only function that calls PyAST_Validate
318 snippets_to_validate = exec_tests + single_tests + eval_tests
319 for snippet in snippets_to_validate:
320 tree = ast.parse(snippet)
321 compile(tree, '<string>', 'exec')
322
Benjamin Peterson78565b22009-06-28 19:19:51 +0000323 def test_slice(self):
324 slc = ast.parse("x[::]").body[0].value.slice
325 self.assertIsNone(slc.upper)
326 self.assertIsNone(slc.lower)
327 self.assertIsNone(slc.step)
328
329 def test_from_import(self):
330 im = ast.parse("from . import y").body[0]
331 self.assertIsNone(im.module)
332
Benjamin Petersona4e4e352012-03-22 08:19:04 -0400333 def test_non_interned_future_from_ast(self):
334 mod = ast.parse("from __future__ import division")
335 self.assertIsInstance(mod.body[0], ast.ImportFrom)
336 mod.body[0].module = " __future__ ".strip()
337 compile(mod, "<test>", "exec")
338
Matthew Suozzo75a06f02021-04-10 16:56:28 -0400339 def test_alias(self):
340 im = ast.parse("from bar import y").body[0]
341 self.assertEqual(len(im.names), 1)
342 alias = im.names[0]
343 self.assertEqual(alias.name, 'y')
344 self.assertIsNone(alias.asname)
345 self.assertEqual(alias.lineno, 1)
346 self.assertEqual(alias.end_lineno, 1)
347 self.assertEqual(alias.col_offset, 16)
348 self.assertEqual(alias.end_col_offset, 17)
349
350 im = ast.parse("from bar import *").body[0]
351 alias = im.names[0]
352 self.assertEqual(alias.name, '*')
353 self.assertIsNone(alias.asname)
354 self.assertEqual(alias.lineno, 1)
355 self.assertEqual(alias.end_lineno, 1)
356 self.assertEqual(alias.col_offset, 16)
357 self.assertEqual(alias.end_col_offset, 17)
358
Benjamin Petersona0dfa822009-11-13 02:25:08 +0000359 def test_base_classes(self):
360 self.assertTrue(issubclass(ast.For, ast.stmt))
361 self.assertTrue(issubclass(ast.Name, ast.expr))
362 self.assertTrue(issubclass(ast.stmt, ast.AST))
363 self.assertTrue(issubclass(ast.expr, ast.AST))
364 self.assertTrue(issubclass(ast.comprehension, ast.AST))
365 self.assertTrue(issubclass(ast.Gt, ast.AST))
366
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500367 def test_field_attr_existence(self):
368 for name, item in ast.__dict__.items():
Batuhan TaĹźkaya397b96f2020-03-01 23:12:17 +0300369 if self._is_ast_node(name, item):
Serhiy Storchaka13d52c22020-03-10 18:52:34 +0200370 if name == 'Index':
371 # Index(value) just returns value now.
372 # The argument is required.
373 continue
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500374 x = item()
375 if isinstance(x, ast.AST):
376 self.assertEqual(type(x._fields), tuple)
377
378 def test_arguments(self):
379 x = ast.arguments()
Pablo Galindocd6e83b2019-07-15 01:32:18 +0200380 self.assertEqual(x._fields, ('posonlyargs', 'args', 'vararg', 'kwonlyargs',
381 'kw_defaults', 'kwarg', 'defaults'))
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500382
383 with self.assertRaises(AttributeError):
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200384 x.args
385 self.assertIsNone(x.vararg)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500386
Pablo Galindo8c77b8c2019-04-29 13:36:57 +0100387 x = ast.arguments(*range(1, 8))
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200388 self.assertEqual(x.args, 2)
Pablo Galindo8c77b8c2019-04-29 13:36:57 +0100389 self.assertEqual(x.vararg, 3)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500390
391 def test_field_attr_writable(self):
392 x = ast.Num()
393 # We can assign to _fields
394 x._fields = 666
395 self.assertEqual(x._fields, 666)
396
397 def test_classattrs(self):
398 x = ast.Num()
Guido van Rossum10f8ce62019-03-13 13:00:46 -0700399 self.assertEqual(x._fields, ('value', 'kind'))
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300400
401 with self.assertRaises(AttributeError):
402 x.value
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500403
404 with self.assertRaises(AttributeError):
405 x.n
406
407 x = ast.Num(42)
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300408 self.assertEqual(x.value, 42)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500409 self.assertEqual(x.n, 42)
410
411 with self.assertRaises(AttributeError):
412 x.lineno
413
414 with self.assertRaises(AttributeError):
415 x.foobar
416
417 x = ast.Num(lineno=2)
418 self.assertEqual(x.lineno, 2)
419
420 x = ast.Num(42, lineno=0)
421 self.assertEqual(x.lineno, 0)
Guido van Rossum10f8ce62019-03-13 13:00:46 -0700422 self.assertEqual(x._fields, ('value', 'kind'))
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300423 self.assertEqual(x.value, 42)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500424 self.assertEqual(x.n, 42)
425
Guido van Rossum10f8ce62019-03-13 13:00:46 -0700426 self.assertRaises(TypeError, ast.Num, 1, None, 2)
427 self.assertRaises(TypeError, ast.Num, 1, None, 2, lineno=0)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500428
Rémi Lapeyrec73914a2020-05-24 23:12:57 +0200429 # Arbitrary keyword arguments are supported
430 self.assertEqual(ast.Constant(1, foo='bar').foo, 'bar')
431 self.assertEqual(ast.Num(1, foo='bar').foo, 'bar')
432
433 with self.assertRaisesRegex(TypeError, "Num got multiple values for argument 'n'"):
434 ast.Num(1, n=2)
435 with self.assertRaisesRegex(TypeError, "Constant got multiple values for argument 'value'"):
436 ast.Constant(1, value=2)
437
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300438 self.assertEqual(ast.Num(42).n, 42)
439 self.assertEqual(ast.Num(4.25).n, 4.25)
440 self.assertEqual(ast.Num(4.25j).n, 4.25j)
441 self.assertEqual(ast.Str('42').s, '42')
442 self.assertEqual(ast.Bytes(b'42').s, b'42')
443 self.assertIs(ast.NameConstant(True).value, True)
444 self.assertIs(ast.NameConstant(False).value, False)
445 self.assertIs(ast.NameConstant(None).value, None)
446
447 self.assertEqual(ast.Constant(42).value, 42)
448 self.assertEqual(ast.Constant(4.25).value, 4.25)
449 self.assertEqual(ast.Constant(4.25j).value, 4.25j)
450 self.assertEqual(ast.Constant('42').value, '42')
451 self.assertEqual(ast.Constant(b'42').value, b'42')
452 self.assertIs(ast.Constant(True).value, True)
453 self.assertIs(ast.Constant(False).value, False)
454 self.assertIs(ast.Constant(None).value, None)
455 self.assertIs(ast.Constant(...).value, ...)
456
457 def test_realtype(self):
458 self.assertEqual(type(ast.Num(42)), ast.Constant)
459 self.assertEqual(type(ast.Num(4.25)), ast.Constant)
460 self.assertEqual(type(ast.Num(4.25j)), ast.Constant)
461 self.assertEqual(type(ast.Str('42')), ast.Constant)
462 self.assertEqual(type(ast.Bytes(b'42')), ast.Constant)
463 self.assertEqual(type(ast.NameConstant(True)), ast.Constant)
464 self.assertEqual(type(ast.NameConstant(False)), ast.Constant)
465 self.assertEqual(type(ast.NameConstant(None)), ast.Constant)
466 self.assertEqual(type(ast.Ellipsis()), ast.Constant)
467
468 def test_isinstance(self):
469 self.assertTrue(isinstance(ast.Num(42), ast.Num))
470 self.assertTrue(isinstance(ast.Num(4.2), ast.Num))
471 self.assertTrue(isinstance(ast.Num(4.2j), ast.Num))
472 self.assertTrue(isinstance(ast.Str('42'), ast.Str))
473 self.assertTrue(isinstance(ast.Bytes(b'42'), ast.Bytes))
474 self.assertTrue(isinstance(ast.NameConstant(True), ast.NameConstant))
475 self.assertTrue(isinstance(ast.NameConstant(False), ast.NameConstant))
476 self.assertTrue(isinstance(ast.NameConstant(None), ast.NameConstant))
477 self.assertTrue(isinstance(ast.Ellipsis(), ast.Ellipsis))
478
479 self.assertTrue(isinstance(ast.Constant(42), ast.Num))
480 self.assertTrue(isinstance(ast.Constant(4.2), ast.Num))
481 self.assertTrue(isinstance(ast.Constant(4.2j), ast.Num))
482 self.assertTrue(isinstance(ast.Constant('42'), ast.Str))
483 self.assertTrue(isinstance(ast.Constant(b'42'), ast.Bytes))
484 self.assertTrue(isinstance(ast.Constant(True), ast.NameConstant))
485 self.assertTrue(isinstance(ast.Constant(False), ast.NameConstant))
486 self.assertTrue(isinstance(ast.Constant(None), ast.NameConstant))
487 self.assertTrue(isinstance(ast.Constant(...), ast.Ellipsis))
488
489 self.assertFalse(isinstance(ast.Str('42'), ast.Num))
490 self.assertFalse(isinstance(ast.Num(42), ast.Str))
491 self.assertFalse(isinstance(ast.Str('42'), ast.Bytes))
492 self.assertFalse(isinstance(ast.Num(42), ast.NameConstant))
493 self.assertFalse(isinstance(ast.Num(42), ast.Ellipsis))
Anthony Sottile74176222019-01-18 11:30:28 -0800494 self.assertFalse(isinstance(ast.NameConstant(True), ast.Num))
495 self.assertFalse(isinstance(ast.NameConstant(False), ast.Num))
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300496
497 self.assertFalse(isinstance(ast.Constant('42'), ast.Num))
498 self.assertFalse(isinstance(ast.Constant(42), ast.Str))
499 self.assertFalse(isinstance(ast.Constant('42'), ast.Bytes))
500 self.assertFalse(isinstance(ast.Constant(42), ast.NameConstant))
501 self.assertFalse(isinstance(ast.Constant(42), ast.Ellipsis))
Anthony Sottile74176222019-01-18 11:30:28 -0800502 self.assertFalse(isinstance(ast.Constant(True), ast.Num))
503 self.assertFalse(isinstance(ast.Constant(False), ast.Num))
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300504
505 self.assertFalse(isinstance(ast.Constant(), ast.Num))
506 self.assertFalse(isinstance(ast.Constant(), ast.Str))
507 self.assertFalse(isinstance(ast.Constant(), ast.Bytes))
508 self.assertFalse(isinstance(ast.Constant(), ast.NameConstant))
509 self.assertFalse(isinstance(ast.Constant(), ast.Ellipsis))
510
Serhiy Storchaka6015cc52018-10-28 13:43:03 +0200511 class S(str): pass
512 self.assertTrue(isinstance(ast.Constant(S('42')), ast.Str))
513 self.assertFalse(isinstance(ast.Constant(S('42')), ast.Num))
514
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300515 def test_subclasses(self):
516 class N(ast.Num):
517 def __init__(self, *args, **kwargs):
518 super().__init__(*args, **kwargs)
519 self.z = 'spam'
520 class N2(ast.Num):
521 pass
522
523 n = N(42)
524 self.assertEqual(n.n, 42)
525 self.assertEqual(n.z, 'spam')
526 self.assertEqual(type(n), N)
527 self.assertTrue(isinstance(n, N))
528 self.assertTrue(isinstance(n, ast.Num))
529 self.assertFalse(isinstance(n, N2))
530 self.assertFalse(isinstance(ast.Num(42), N))
531 n = N(n=42)
532 self.assertEqual(n.n, 42)
533 self.assertEqual(type(n), N)
534
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500535 def test_module(self):
536 body = [ast.Num(42)]
Guido van Rossumdcfcd142019-01-31 03:40:27 -0800537 x = ast.Module(body, [])
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500538 self.assertEqual(x.body, body)
539
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000540 def test_nodeclasses(self):
Florent Xicluna992d9e02011-11-11 19:35:42 +0100541 # Zero arguments constructor explicitly allowed
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500542 x = ast.BinOp()
543 self.assertEqual(x._fields, ('left', 'op', 'right'))
544
545 # Random attribute allowed too
546 x.foobarbaz = 5
547 self.assertEqual(x.foobarbaz, 5)
548
549 n1 = ast.Num(1)
550 n3 = ast.Num(3)
551 addop = ast.Add()
552 x = ast.BinOp(n1, addop, n3)
553 self.assertEqual(x.left, n1)
554 self.assertEqual(x.op, addop)
555 self.assertEqual(x.right, n3)
Benjamin Peterson68b543a2011-06-27 17:51:18 -0500556
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500557 x = ast.BinOp(1, 2, 3)
558 self.assertEqual(x.left, 1)
559 self.assertEqual(x.op, 2)
560 self.assertEqual(x.right, 3)
561
Georg Brandl0c77a822008-06-10 16:37:50 +0000562 x = ast.BinOp(1, 2, 3, lineno=0)
Ezio Melottib3aedd42010-11-20 19:04:17 +0000563 self.assertEqual(x.left, 1)
564 self.assertEqual(x.op, 2)
565 self.assertEqual(x.right, 3)
566 self.assertEqual(x.lineno, 0)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000567
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500568 # node raises exception when given too many arguments
569 self.assertRaises(TypeError, ast.BinOp, 1, 2, 3, 4)
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500570 # node raises exception when given too many arguments
571 self.assertRaises(TypeError, ast.BinOp, 1, 2, 3, 4, lineno=0)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000572
573 # can set attributes through kwargs too
Georg Brandl0c77a822008-06-10 16:37:50 +0000574 x = ast.BinOp(left=1, op=2, right=3, lineno=0)
Ezio Melottib3aedd42010-11-20 19:04:17 +0000575 self.assertEqual(x.left, 1)
576 self.assertEqual(x.op, 2)
577 self.assertEqual(x.right, 3)
578 self.assertEqual(x.lineno, 0)
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000579
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500580 # Random kwargs also allowed
581 x = ast.BinOp(1, 2, 3, foobarbaz=42)
582 self.assertEqual(x.foobarbaz, 42)
583
584 def test_no_fields(self):
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000585 # this used to fail because Sub._fields was None
Georg Brandl0c77a822008-06-10 16:37:50 +0000586 x = ast.Sub()
Benjamin Peterson6ccfe852011-06-27 17:46:06 -0500587 self.assertEqual(x._fields, ())
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000588
589 def test_pickling(self):
590 import pickle
591 mods = [pickle]
592 try:
593 import cPickle
594 mods.append(cPickle)
595 except ImportError:
596 pass
597 protocols = [0, 1, 2]
598 for mod in mods:
599 for protocol in protocols:
600 for ast in (compile(i, "?", "exec", 0x400) for i in exec_tests):
601 ast2 = mod.loads(mod.dumps(ast, protocol))
Ezio Melottib3aedd42010-11-20 19:04:17 +0000602 self.assertEqual(to_tuple(ast2), to_tuple(ast))
Neal Norwitzee9b10a2008-03-31 05:29:39 +0000603
Benjamin Peterson5b066812010-11-20 01:38:49 +0000604 def test_invalid_sum(self):
605 pos = dict(lineno=2, col_offset=3)
Guido van Rossumdcfcd142019-01-31 03:40:27 -0800606 m = ast.Module([ast.Expr(ast.expr(**pos), **pos)], [])
Benjamin Peterson5b066812010-11-20 01:38:49 +0000607 with self.assertRaises(TypeError) as cm:
608 compile(m, "<test>", "exec")
Serhiy Storchakabace59d2020-03-22 20:33:34 +0200609 self.assertIn("but got <ast.expr", str(cm.exception))
Benjamin Peterson5b066812010-11-20 01:38:49 +0000610
Min ho Kimc4cacc82019-07-31 08:16:13 +1000611 def test_invalid_identifier(self):
Guido van Rossumdcfcd142019-01-31 03:40:27 -0800612 m = ast.Module([ast.Expr(ast.Name(42, ast.Load()))], [])
Benjamin Peterson2193d2b2011-07-22 10:50:23 -0500613 ast.fix_missing_locations(m)
614 with self.assertRaises(TypeError) as cm:
615 compile(m, "<test>", "exec")
616 self.assertIn("identifier must be of type str", str(cm.exception))
617
Batuhan TaĹźkaya0ac59f92020-03-19 14:32:28 +0300618 def test_invalid_constant(self):
619 for invalid_constant in int, (1, 2, int), frozenset((1, 2, int)):
620 e = ast.Expression(body=ast.Constant(invalid_constant))
621 ast.fix_missing_locations(e)
622 with self.assertRaisesRegex(
623 TypeError, "invalid type in Constant: type"
624 ):
625 compile(e, "<test>", "eval")
626
Mark Dickinsonded35ae2012-11-25 14:36:26 +0000627 def test_empty_yield_from(self):
628 # Issue 16546: yield from value is not optional.
629 empty_yield_from = ast.parse("def f():\n yield from g()")
630 empty_yield_from.body[0].body[0].value.value = None
631 with self.assertRaises(ValueError) as cm:
632 compile(empty_yield_from, "<test>", "exec")
Batuhan Taskaya091951a2020-05-06 17:29:32 +0300633 self.assertIn("field 'value' is required", str(cm.exception))
Mark Dickinsonded35ae2012-11-25 14:36:26 +0000634
Oren Milman7dc46d82017-09-30 20:16:24 +0300635 @support.cpython_only
636 def test_issue31592(self):
637 # There shouldn't be an assertion failure in case of a bad
638 # unicodedata.normalize().
639 import unicodedata
640 def bad_normalize(*args):
641 return None
642 with support.swap_attr(unicodedata, 'normalize', bad_normalize):
643 self.assertRaises(TypeError, ast.parse, '\u03D5')
644
Carl Friedrich Bolz-Tereick110a47c2019-07-08 23:17:56 +0200645 def test_issue18374_binop_col_offset(self):
646 tree = ast.parse('4+5+6+7')
647 parent_binop = tree.body[0].value
648 child_binop = parent_binop.left
649 grandchild_binop = child_binop.left
650 self.assertEqual(parent_binop.col_offset, 0)
651 self.assertEqual(parent_binop.end_col_offset, 7)
652 self.assertEqual(child_binop.col_offset, 0)
653 self.assertEqual(child_binop.end_col_offset, 5)
654 self.assertEqual(grandchild_binop.col_offset, 0)
655 self.assertEqual(grandchild_binop.end_col_offset, 3)
656
657 tree = ast.parse('4+5-\\\n 6-7')
658 parent_binop = tree.body[0].value
659 child_binop = parent_binop.left
660 grandchild_binop = child_binop.left
661 self.assertEqual(parent_binop.col_offset, 0)
662 self.assertEqual(parent_binop.lineno, 1)
663 self.assertEqual(parent_binop.end_col_offset, 4)
664 self.assertEqual(parent_binop.end_lineno, 2)
665
666 self.assertEqual(child_binop.col_offset, 0)
Carl Friedrich Bolz-Tereick430a9f42019-07-09 14:20:01 +0200667 self.assertEqual(child_binop.lineno, 1)
Carl Friedrich Bolz-Tereick110a47c2019-07-08 23:17:56 +0200668 self.assertEqual(child_binop.end_col_offset, 2)
Carl Friedrich Bolz-Tereick430a9f42019-07-09 14:20:01 +0200669 self.assertEqual(child_binop.end_lineno, 2)
Carl Friedrich Bolz-Tereick110a47c2019-07-08 23:17:56 +0200670
671 self.assertEqual(grandchild_binop.col_offset, 0)
Carl Friedrich Bolz-Tereick430a9f42019-07-09 14:20:01 +0200672 self.assertEqual(grandchild_binop.lineno, 1)
Carl Friedrich Bolz-Tereick110a47c2019-07-08 23:17:56 +0200673 self.assertEqual(grandchild_binop.end_col_offset, 3)
Carl Friedrich Bolz-Tereick430a9f42019-07-09 14:20:01 +0200674 self.assertEqual(grandchild_binop.end_lineno, 1)
Georg Brandl0c77a822008-06-10 16:37:50 +0000675
Lysandros Nikolaoud2e10982020-02-08 00:36:32 +0100676 def test_issue39579_dotted_name_end_col_offset(self):
677 tree = ast.parse('@a.b.c\ndef f(): pass')
678 attr_b = tree.body[0].decorator_list[0].value
679 self.assertEqual(attr_b.end_col_offset, 4)
680
Batuhan TaĹźkaya4ab362c2020-03-16 11:12:53 +0300681 def test_ast_asdl_signature(self):
682 self.assertEqual(ast.withitem.__doc__, "withitem(expr context_expr, expr? optional_vars)")
683 self.assertEqual(ast.GtE.__doc__, "GtE")
684 self.assertEqual(ast.Name.__doc__, "Name(identifier id, expr_context ctx)")
685 self.assertEqual(ast.cmpop.__doc__, "cmpop = Eq | NotEq | Lt | LtE | Gt | GtE | Is | IsNot | In | NotIn")
686 expressions = [f" | {node.__doc__}" for node in ast.expr.__subclasses__()]
687 expressions[0] = f"expr = {ast.expr.__subclasses__()[0].__doc__}"
688 self.assertCountEqual(ast.expr.__doc__.split("\n"), expressions)
689
Shantanuc116c942020-05-27 13:30:38 -0700690 def test_issue40614_feature_version(self):
691 ast.parse('f"{x=}"', feature_version=(3, 8))
692 with self.assertRaises(SyntaxError):
693 ast.parse('f"{x=}"', feature_version=(3, 7))
694
Batuhan Taskaya68874a82020-06-06 15:44:16 +0300695 def test_constant_as_name(self):
696 for constant in "True", "False", "None":
697 expr = ast.Expression(ast.Name(constant, ast.Load()))
698 ast.fix_missing_locations(expr)
699 with self.assertRaisesRegex(ValueError, f"Name node can't be used with '{constant}' constant"):
700 compile(expr, "<test>", "eval")
701
Ethan Furmana02cb472021-04-21 10:20:44 -0700702 def test_precedence_enum(self):
703 class _Precedence(enum.IntEnum):
704 """Precedence table that originated from python grammar."""
705 TUPLE = enum.auto()
706 YIELD = enum.auto() # 'yield', 'yield from'
707 TEST = enum.auto() # 'if'-'else', 'lambda'
708 OR = enum.auto() # 'or'
709 AND = enum.auto() # 'and'
710 NOT = enum.auto() # 'not'
711 CMP = enum.auto() # '<', '>', '==', '>=', '<=', '!=',
712 # 'in', 'not in', 'is', 'is not'
713 EXPR = enum.auto()
714 BOR = EXPR # '|'
715 BXOR = enum.auto() # '^'
716 BAND = enum.auto() # '&'
717 SHIFT = enum.auto() # '<<', '>>'
718 ARITH = enum.auto() # '+', '-'
719 TERM = enum.auto() # '*', '@', '/', '%', '//'
720 FACTOR = enum.auto() # unary '+', '-', '~'
721 POWER = enum.auto() # '**'
722 AWAIT = enum.auto() # 'await'
723 ATOM = enum.auto()
724 def next(self):
725 try:
726 return self.__class__(self + 1)
727 except ValueError:
728 return self
729 enum._test_simple_enum(_Precedence, ast._Precedence)
730
Batuhan TaĹźkaya4ab362c2020-03-16 11:12:53 +0300731
Georg Brandl0c77a822008-06-10 16:37:50 +0000732class ASTHelpers_Test(unittest.TestCase):
Guido van Rossum10f8ce62019-03-13 13:00:46 -0700733 maxDiff = None
Georg Brandl0c77a822008-06-10 16:37:50 +0000734
735 def test_parse(self):
736 a = ast.parse('foo(1 + 1)')
737 b = compile('foo(1 + 1)', '<unknown>', 'exec', ast.PyCF_ONLY_AST)
738 self.assertEqual(ast.dump(a), ast.dump(b))
739
Benjamin Peterson2e2c9032012-09-02 14:23:15 -0400740 def test_parse_in_error(self):
741 try:
742 1/0
743 except Exception:
Benjamin Petersonbd0df502012-09-02 15:04:51 -0400744 with self.assertRaises(SyntaxError) as e:
745 ast.literal_eval(r"'\U'")
746 self.assertIsNotNone(e.exception.__context__)
Benjamin Peterson2e2c9032012-09-02 14:23:15 -0400747
Georg Brandl0c77a822008-06-10 16:37:50 +0000748 def test_dump(self):
749 node = ast.parse('spam(eggs, "and cheese")')
750 self.assertEqual(ast.dump(node),
751 "Module(body=[Expr(value=Call(func=Name(id='spam', ctx=Load()), "
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200752 "args=[Name(id='eggs', ctx=Load()), Constant(value='and cheese')], "
Guido van Rossumdcfcd142019-01-31 03:40:27 -0800753 "keywords=[]))], type_ignores=[])"
Georg Brandl0c77a822008-06-10 16:37:50 +0000754 )
755 self.assertEqual(ast.dump(node, annotate_fields=False),
756 "Module([Expr(Call(Name('spam', Load()), [Name('eggs', Load()), "
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200757 "Constant('and cheese')], []))], [])"
Georg Brandl0c77a822008-06-10 16:37:50 +0000758 )
759 self.assertEqual(ast.dump(node, include_attributes=True),
760 "Module(body=[Expr(value=Call(func=Name(id='spam', ctx=Load(), "
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000761 "lineno=1, col_offset=0, end_lineno=1, end_col_offset=4), "
762 "args=[Name(id='eggs', ctx=Load(), lineno=1, col_offset=5, "
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200763 "end_lineno=1, end_col_offset=9), Constant(value='and cheese', "
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000764 "lineno=1, col_offset=11, end_lineno=1, end_col_offset=23)], keywords=[], "
765 "lineno=1, col_offset=0, end_lineno=1, end_col_offset=24), "
Guido van Rossumdcfcd142019-01-31 03:40:27 -0800766 "lineno=1, col_offset=0, end_lineno=1, end_col_offset=24)], type_ignores=[])"
Georg Brandl0c77a822008-06-10 16:37:50 +0000767 )
768
Serhiy Storchaka850573b2019-09-09 19:33:13 +0300769 def test_dump_indent(self):
770 node = ast.parse('spam(eggs, "and cheese")')
771 self.assertEqual(ast.dump(node, indent=3), """\
772Module(
773 body=[
774 Expr(
775 value=Call(
776 func=Name(id='spam', ctx=Load()),
777 args=[
778 Name(id='eggs', ctx=Load()),
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200779 Constant(value='and cheese')],
Serhiy Storchaka850573b2019-09-09 19:33:13 +0300780 keywords=[]))],
781 type_ignores=[])""")
782 self.assertEqual(ast.dump(node, annotate_fields=False, indent='\t'), """\
783Module(
784\t[
785\t\tExpr(
786\t\t\tCall(
787\t\t\t\tName('spam', Load()),
788\t\t\t\t[
789\t\t\t\t\tName('eggs', Load()),
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200790\t\t\t\t\tConstant('and cheese')],
Serhiy Storchaka850573b2019-09-09 19:33:13 +0300791\t\t\t\t[]))],
792\t[])""")
793 self.assertEqual(ast.dump(node, include_attributes=True, indent=3), """\
794Module(
795 body=[
796 Expr(
797 value=Call(
798 func=Name(
799 id='spam',
800 ctx=Load(),
801 lineno=1,
802 col_offset=0,
803 end_lineno=1,
804 end_col_offset=4),
805 args=[
806 Name(
807 id='eggs',
808 ctx=Load(),
809 lineno=1,
810 col_offset=5,
811 end_lineno=1,
812 end_col_offset=9),
813 Constant(
814 value='and cheese',
Serhiy Storchaka850573b2019-09-09 19:33:13 +0300815 lineno=1,
816 col_offset=11,
817 end_lineno=1,
818 end_col_offset=23)],
819 keywords=[],
820 lineno=1,
821 col_offset=0,
822 end_lineno=1,
823 end_col_offset=24),
824 lineno=1,
825 col_offset=0,
826 end_lineno=1,
827 end_col_offset=24)],
828 type_ignores=[])""")
829
Serhiy Storchakae64f9482019-08-29 09:30:23 +0300830 def test_dump_incomplete(self):
831 node = ast.Raise(lineno=3, col_offset=4)
832 self.assertEqual(ast.dump(node),
833 "Raise()"
834 )
835 self.assertEqual(ast.dump(node, include_attributes=True),
836 "Raise(lineno=3, col_offset=4)"
837 )
838 node = ast.Raise(exc=ast.Name(id='e', ctx=ast.Load()), lineno=3, col_offset=4)
839 self.assertEqual(ast.dump(node),
840 "Raise(exc=Name(id='e', ctx=Load()))"
841 )
842 self.assertEqual(ast.dump(node, annotate_fields=False),
843 "Raise(Name('e', Load()))"
844 )
845 self.assertEqual(ast.dump(node, include_attributes=True),
846 "Raise(exc=Name(id='e', ctx=Load()), lineno=3, col_offset=4)"
847 )
848 self.assertEqual(ast.dump(node, annotate_fields=False, include_attributes=True),
849 "Raise(Name('e', Load()), lineno=3, col_offset=4)"
850 )
851 node = ast.Raise(cause=ast.Name(id='e', ctx=ast.Load()))
852 self.assertEqual(ast.dump(node),
853 "Raise(cause=Name(id='e', ctx=Load()))"
854 )
855 self.assertEqual(ast.dump(node, annotate_fields=False),
856 "Raise(cause=Name('e', Load()))"
857 )
858
Georg Brandl0c77a822008-06-10 16:37:50 +0000859 def test_copy_location(self):
860 src = ast.parse('1 + 1', mode='eval')
861 src.body.right = ast.copy_location(ast.Num(2), src.body.right)
862 self.assertEqual(ast.dump(src, include_attributes=True),
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200863 'Expression(body=BinOp(left=Constant(value=1, lineno=1, col_offset=0, '
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000864 'end_lineno=1, end_col_offset=1), op=Add(), right=Constant(value=2, '
865 'lineno=1, col_offset=4, end_lineno=1, end_col_offset=5), lineno=1, '
866 'col_offset=0, end_lineno=1, end_col_offset=5))'
Georg Brandl0c77a822008-06-10 16:37:50 +0000867 )
Batuhan Taskaya8f4380d2020-08-05 16:32:32 +0300868 src = ast.Call(col_offset=1, lineno=1, end_lineno=1, end_col_offset=1)
869 new = ast.copy_location(src, ast.Call(col_offset=None, lineno=None))
870 self.assertIsNone(new.end_lineno)
871 self.assertIsNone(new.end_col_offset)
872 self.assertEqual(new.lineno, 1)
873 self.assertEqual(new.col_offset, 1)
Georg Brandl0c77a822008-06-10 16:37:50 +0000874
875 def test_fix_missing_locations(self):
876 src = ast.parse('write("spam")')
877 src.body.append(ast.Expr(ast.Call(ast.Name('spam', ast.Load()),
Benjamin Peterson025e9eb2015-05-05 20:16:41 -0400878 [ast.Str('eggs')], [])))
Georg Brandl0c77a822008-06-10 16:37:50 +0000879 self.assertEqual(src, ast.fix_missing_locations(src))
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000880 self.maxDiff = None
Georg Brandl0c77a822008-06-10 16:37:50 +0000881 self.assertEqual(ast.dump(src, include_attributes=True),
882 "Module(body=[Expr(value=Call(func=Name(id='write', ctx=Load(), "
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000883 "lineno=1, col_offset=0, end_lineno=1, end_col_offset=5), "
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200884 "args=[Constant(value='spam', lineno=1, col_offset=6, end_lineno=1, "
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000885 "end_col_offset=12)], keywords=[], lineno=1, col_offset=0, end_lineno=1, "
886 "end_col_offset=13), lineno=1, col_offset=0, end_lineno=1, "
887 "end_col_offset=13), Expr(value=Call(func=Name(id='spam', ctx=Load(), "
888 "lineno=1, col_offset=0, end_lineno=1, end_col_offset=0), "
889 "args=[Constant(value='eggs', lineno=1, col_offset=0, end_lineno=1, "
890 "end_col_offset=0)], keywords=[], lineno=1, col_offset=0, end_lineno=1, "
Guido van Rossumdcfcd142019-01-31 03:40:27 -0800891 "end_col_offset=0), lineno=1, col_offset=0, end_lineno=1, end_col_offset=0)], "
892 "type_ignores=[])"
Georg Brandl0c77a822008-06-10 16:37:50 +0000893 )
894
895 def test_increment_lineno(self):
896 src = ast.parse('1 + 1', mode='eval')
897 self.assertEqual(ast.increment_lineno(src, n=3), src)
898 self.assertEqual(ast.dump(src, include_attributes=True),
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200899 'Expression(body=BinOp(left=Constant(value=1, lineno=4, col_offset=0, '
900 'end_lineno=4, end_col_offset=1), op=Add(), right=Constant(value=1, '
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000901 'lineno=4, col_offset=4, end_lineno=4, end_col_offset=5), lineno=4, '
902 'col_offset=0, end_lineno=4, end_col_offset=5))'
Georg Brandl0c77a822008-06-10 16:37:50 +0000903 )
Georg Brandl619e7ba2011-01-09 07:38:51 +0000904 # issue10869: do not increment lineno of root twice
Georg Brandlefb69022011-01-09 07:50:48 +0000905 src = ast.parse('1 + 1', mode='eval')
Georg Brandl619e7ba2011-01-09 07:38:51 +0000906 self.assertEqual(ast.increment_lineno(src.body, n=3), src.body)
907 self.assertEqual(ast.dump(src, include_attributes=True),
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200908 'Expression(body=BinOp(left=Constant(value=1, lineno=4, col_offset=0, '
909 'end_lineno=4, end_col_offset=1), op=Add(), right=Constant(value=1, '
Ivan Levkivskyi9932a222019-01-22 11:18:22 +0000910 'lineno=4, col_offset=4, end_lineno=4, end_col_offset=5), lineno=4, '
911 'col_offset=0, end_lineno=4, end_col_offset=5))'
Georg Brandl619e7ba2011-01-09 07:38:51 +0000912 )
Batuhan Taskaya8f4380d2020-08-05 16:32:32 +0300913 src = ast.Call(
914 func=ast.Name("test", ast.Load()), args=[], keywords=[], lineno=1
915 )
916 self.assertEqual(ast.increment_lineno(src).lineno, 2)
917 self.assertIsNone(ast.increment_lineno(src).end_lineno)
Georg Brandl0c77a822008-06-10 16:37:50 +0000918
919 def test_iter_fields(self):
920 node = ast.parse('foo()', mode='eval')
921 d = dict(ast.iter_fields(node.body))
922 self.assertEqual(d.pop('func').id, 'foo')
Benjamin Peterson025e9eb2015-05-05 20:16:41 -0400923 self.assertEqual(d, {'keywords': [], 'args': []})
Georg Brandl0c77a822008-06-10 16:37:50 +0000924
925 def test_iter_child_nodes(self):
926 node = ast.parse("spam(23, 42, eggs='leek')", mode='eval')
927 self.assertEqual(len(list(ast.iter_child_nodes(node.body))), 4)
928 iterator = ast.iter_child_nodes(node.body)
929 self.assertEqual(next(iterator).id, 'spam')
Serhiy Storchaka3f228112018-09-27 17:42:37 +0300930 self.assertEqual(next(iterator).value, 23)
931 self.assertEqual(next(iterator).value, 42)
Georg Brandl0c77a822008-06-10 16:37:50 +0000932 self.assertEqual(ast.dump(next(iterator)),
Serhiy Storchakab7e95252020-03-10 00:07:47 +0200933 "keyword(arg='eggs', value=Constant(value='leek'))"
Georg Brandl0c77a822008-06-10 16:37:50 +0000934 )
935
936 def test_get_docstring(self):
Serhiy Storchaka08f127a2018-06-15 11:05:15 +0300937 node = ast.parse('"""line one\n line two"""')
938 self.assertEqual(ast.get_docstring(node),
939 'line one\nline two')
940
941 node = ast.parse('class foo:\n """line one\n line two"""')
942 self.assertEqual(ast.get_docstring(node.body[0]),
943 'line one\nline two')
944
Georg Brandl0c77a822008-06-10 16:37:50 +0000945 node = ast.parse('def foo():\n """line one\n line two"""')
946 self.assertEqual(ast.get_docstring(node.body[0]),
947 'line one\nline two')
948
Yury Selivanov2f07a662015-07-23 08:54:35 +0300949 node = ast.parse('async def foo():\n """spam\n ham"""')
950 self.assertEqual(ast.get_docstring(node.body[0]), 'spam\nham')
Serhiy Storchaka08f127a2018-06-15 11:05:15 +0300951
952 def test_get_docstring_none(self):
Matthias Bussonnier41cea702017-02-23 22:44:19 -0800953 self.assertIsNone(ast.get_docstring(ast.parse('')))
Serhiy Storchaka08f127a2018-06-15 11:05:15 +0300954 node = ast.parse('x = "not docstring"')
955 self.assertIsNone(ast.get_docstring(node))
956 node = ast.parse('def foo():\n pass')
957 self.assertIsNone(ast.get_docstring(node))
958
959 node = ast.parse('class foo:\n pass')
960 self.assertIsNone(ast.get_docstring(node.body[0]))
961 node = ast.parse('class foo:\n x = "not docstring"')
962 self.assertIsNone(ast.get_docstring(node.body[0]))
963 node = ast.parse('class foo:\n def bar(self): pass')
964 self.assertIsNone(ast.get_docstring(node.body[0]))
965
966 node = ast.parse('def foo():\n pass')
967 self.assertIsNone(ast.get_docstring(node.body[0]))
968 node = ast.parse('def foo():\n x = "not docstring"')
969 self.assertIsNone(ast.get_docstring(node.body[0]))
970
971 node = ast.parse('async def foo():\n pass')
972 self.assertIsNone(ast.get_docstring(node.body[0]))
973 node = ast.parse('async def foo():\n x = "not docstring"')
974 self.assertIsNone(ast.get_docstring(node.body[0]))
Yury Selivanov2f07a662015-07-23 08:54:35 +0300975
Anthony Sottile995d9b92019-01-12 20:05:13 -0800976 def test_multi_line_docstring_col_offset_and_lineno_issue16806(self):
977 node = ast.parse(
978 '"""line one\nline two"""\n\n'
979 'def foo():\n """line one\n line two"""\n\n'
980 ' def bar():\n """line one\n line two"""\n'
981 ' """line one\n line two"""\n'
982 '"""line one\nline two"""\n\n'
983 )
984 self.assertEqual(node.body[0].col_offset, 0)
985 self.assertEqual(node.body[0].lineno, 1)
986 self.assertEqual(node.body[1].body[0].col_offset, 2)
987 self.assertEqual(node.body[1].body[0].lineno, 5)
988 self.assertEqual(node.body[1].body[1].body[0].col_offset, 4)
989 self.assertEqual(node.body[1].body[1].body[0].lineno, 9)
990 self.assertEqual(node.body[1].body[2].col_offset, 2)
991 self.assertEqual(node.body[1].body[2].lineno, 11)
992 self.assertEqual(node.body[2].col_offset, 0)
993 self.assertEqual(node.body[2].lineno, 13)
994
Lysandros Nikolaou025a6022019-12-12 22:40:21 +0100995 def test_elif_stmt_start_position(self):
996 node = ast.parse('if a:\n pass\nelif b:\n pass\n')
997 elif_stmt = node.body[0].orelse[0]
998 self.assertEqual(elif_stmt.lineno, 3)
999 self.assertEqual(elif_stmt.col_offset, 0)
1000
Lysandros Nikolaou5936a4c2019-12-14 11:24:57 +01001001 def test_elif_stmt_start_position_with_else(self):
1002 node = ast.parse('if a:\n pass\nelif b:\n pass\nelse:\n pass\n')
1003 elif_stmt = node.body[0].orelse[0]
1004 self.assertEqual(elif_stmt.lineno, 3)
1005 self.assertEqual(elif_stmt.col_offset, 0)
1006
Lysandros Nikolaou50d4f122019-12-18 01:20:55 +01001007 def test_starred_expr_end_position_within_call(self):
1008 node = ast.parse('f(*[0, 1])')
1009 starred_expr = node.body[0].value.args[0]
1010 self.assertEqual(starred_expr.end_lineno, 1)
1011 self.assertEqual(starred_expr.end_col_offset, 9)
1012
Georg Brandl0c77a822008-06-10 16:37:50 +00001013 def test_literal_eval(self):
1014 self.assertEqual(ast.literal_eval('[1, 2, 3]'), [1, 2, 3])
1015 self.assertEqual(ast.literal_eval('{"foo": 42}'), {"foo": 42})
1016 self.assertEqual(ast.literal_eval('(True, False, None)'), (True, False, None))
Benjamin Peterson3e742892010-07-11 12:59:24 +00001017 self.assertEqual(ast.literal_eval('{1, 2, 3}'), {1, 2, 3})
Benjamin Peterson5ef96e52010-07-11 23:06:06 +00001018 self.assertEqual(ast.literal_eval('b"hi"'), b"hi")
Raymond Hettinger4fcf5c12020-01-02 22:21:18 -07001019 self.assertEqual(ast.literal_eval('set()'), set())
Georg Brandl0c77a822008-06-10 16:37:50 +00001020 self.assertRaises(ValueError, ast.literal_eval, 'foo()')
Serhiy Storchakad8ac4d12018-01-04 11:15:39 +02001021 self.assertEqual(ast.literal_eval('6'), 6)
1022 self.assertEqual(ast.literal_eval('+6'), 6)
Raymond Hettingerbc959732010-10-08 00:47:45 +00001023 self.assertEqual(ast.literal_eval('-6'), -6)
Raymond Hettingerbc959732010-10-08 00:47:45 +00001024 self.assertEqual(ast.literal_eval('3.25'), 3.25)
Serhiy Storchakad8ac4d12018-01-04 11:15:39 +02001025 self.assertEqual(ast.literal_eval('+3.25'), 3.25)
1026 self.assertEqual(ast.literal_eval('-3.25'), -3.25)
1027 self.assertEqual(repr(ast.literal_eval('-0.0')), '-0.0')
1028 self.assertRaises(ValueError, ast.literal_eval, '++6')
1029 self.assertRaises(ValueError, ast.literal_eval, '+True')
1030 self.assertRaises(ValueError, ast.literal_eval, '2+3')
Georg Brandl0c77a822008-06-10 16:37:50 +00001031
Serhiy Storchakad8ac4d12018-01-04 11:15:39 +02001032 def test_literal_eval_complex(self):
1033 # Issue #4907
1034 self.assertEqual(ast.literal_eval('6j'), 6j)
1035 self.assertEqual(ast.literal_eval('-6j'), -6j)
1036 self.assertEqual(ast.literal_eval('6.75j'), 6.75j)
1037 self.assertEqual(ast.literal_eval('-6.75j'), -6.75j)
1038 self.assertEqual(ast.literal_eval('3+6j'), 3+6j)
1039 self.assertEqual(ast.literal_eval('-3+6j'), -3+6j)
1040 self.assertEqual(ast.literal_eval('3-6j'), 3-6j)
1041 self.assertEqual(ast.literal_eval('-3-6j'), -3-6j)
1042 self.assertEqual(ast.literal_eval('3.25+6.75j'), 3.25+6.75j)
1043 self.assertEqual(ast.literal_eval('-3.25+6.75j'), -3.25+6.75j)
1044 self.assertEqual(ast.literal_eval('3.25-6.75j'), 3.25-6.75j)
1045 self.assertEqual(ast.literal_eval('-3.25-6.75j'), -3.25-6.75j)
1046 self.assertEqual(ast.literal_eval('(3+6j)'), 3+6j)
1047 self.assertRaises(ValueError, ast.literal_eval, '-6j+3')
1048 self.assertRaises(ValueError, ast.literal_eval, '-6j+3j')
1049 self.assertRaises(ValueError, ast.literal_eval, '3+-6j')
1050 self.assertRaises(ValueError, ast.literal_eval, '3+(0+6j)')
1051 self.assertRaises(ValueError, ast.literal_eval, '-(3+6j)')
Benjamin Peterson058e31e2009-01-16 03:54:08 +00001052
Curtis Bucherc21c5122020-05-05 12:40:56 -07001053 def test_literal_eval_malformed_dict_nodes(self):
1054 malformed = ast.Dict(keys=[ast.Constant(1), ast.Constant(2)], values=[ast.Constant(3)])
1055 self.assertRaises(ValueError, ast.literal_eval, malformed)
1056 malformed = ast.Dict(keys=[ast.Constant(1)], values=[ast.Constant(2), ast.Constant(3)])
1057 self.assertRaises(ValueError, ast.literal_eval, malformed)
1058
Batuhan Taskayae799aa82020-10-04 03:46:44 +03001059 def test_literal_eval_trailing_ws(self):
1060 self.assertEqual(ast.literal_eval(" -1"), -1)
1061 self.assertEqual(ast.literal_eval("\t\t-1"), -1)
1062 self.assertEqual(ast.literal_eval(" \t -1"), -1)
1063 self.assertRaises(IndentationError, ast.literal_eval, "\n -1")
1064
Irit Katriel586f3db2020-12-25 17:04:31 +00001065 def test_literal_eval_malformed_lineno(self):
1066 msg = r'malformed node or string on line 3:'
1067 with self.assertRaisesRegex(ValueError, msg):
1068 ast.literal_eval("{'a': 1,\n'b':2,\n'c':++3,\n'd':4}")
1069
1070 node = ast.UnaryOp(
1071 ast.UAdd(), ast.UnaryOp(ast.UAdd(), ast.Constant(6)))
1072 self.assertIsNone(getattr(node, 'lineno', None))
1073 msg = r'malformed node or string:'
1074 with self.assertRaisesRegex(ValueError, msg):
1075 ast.literal_eval(node)
1076
Amaury Forgeot d'Arc58e87612011-11-22 21:51:55 +01001077 def test_bad_integer(self):
1078 # issue13436: Bad error message with invalid numeric values
1079 body = [ast.ImportFrom(module='time',
1080 names=[ast.alias(name='sleep')],
1081 level=None,
1082 lineno=None, col_offset=None)]
Guido van Rossumdcfcd142019-01-31 03:40:27 -08001083 mod = ast.Module(body, [])
Amaury Forgeot d'Arc58e87612011-11-22 21:51:55 +01001084 with self.assertRaises(ValueError) as cm:
1085 compile(mod, 'test', 'exec')
1086 self.assertIn("invalid integer value: None", str(cm.exception))
1087
Berker Peksag0a5bd512016-04-29 19:50:02 +03001088 def test_level_as_none(self):
1089 body = [ast.ImportFrom(module='time',
Matthew Suozzo75a06f02021-04-10 16:56:28 -04001090 names=[ast.alias(name='sleep',
1091 lineno=0, col_offset=0)],
Berker Peksag0a5bd512016-04-29 19:50:02 +03001092 level=None,
1093 lineno=0, col_offset=0)]
Guido van Rossumdcfcd142019-01-31 03:40:27 -08001094 mod = ast.Module(body, [])
Berker Peksag0a5bd512016-04-29 19:50:02 +03001095 code = compile(mod, 'test', 'exec')
1096 ns = {}
1097 exec(code, ns)
1098 self.assertIn('sleep', ns)
1099
Miss Islington (bot)976598d2021-06-03 13:27:00 -07001100 def test_recursion_direct(self):
1101 e = ast.UnaryOp(op=ast.Not(), lineno=0, col_offset=0)
1102 e.operand = e
1103 with self.assertRaises(RecursionError):
Batuhan Taskayabd6f0d32021-06-08 20:39:30 +03001104 with support.infinite_recursion():
1105 compile(ast.Expression(e), "<test>", "eval")
Miss Islington (bot)976598d2021-06-03 13:27:00 -07001106
1107 def test_recursion_indirect(self):
1108 e = ast.UnaryOp(op=ast.Not(), lineno=0, col_offset=0)
1109 f = ast.UnaryOp(op=ast.Not(), lineno=0, col_offset=0)
1110 e.operand = f
1111 f.operand = e
1112 with self.assertRaises(RecursionError):
Batuhan Taskayabd6f0d32021-06-08 20:39:30 +03001113 with support.infinite_recursion():
1114 compile(ast.Expression(e), "<test>", "eval")
Miss Islington (bot)976598d2021-06-03 13:27:00 -07001115
Georg Brandl0c77a822008-06-10 16:37:50 +00001116
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001117class ASTValidatorTests(unittest.TestCase):
1118
1119 def mod(self, mod, msg=None, mode="exec", *, exc=ValueError):
1120 mod.lineno = mod.col_offset = 0
1121 ast.fix_missing_locations(mod)
Serhiy Storchaka3f228112018-09-27 17:42:37 +03001122 if msg is None:
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001123 compile(mod, "<test>", mode)
Serhiy Storchaka3f228112018-09-27 17:42:37 +03001124 else:
1125 with self.assertRaises(exc) as cm:
1126 compile(mod, "<test>", mode)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001127 self.assertIn(msg, str(cm.exception))
1128
1129 def expr(self, node, msg=None, *, exc=ValueError):
Guido van Rossumdcfcd142019-01-31 03:40:27 -08001130 mod = ast.Module([ast.Expr(node)], [])
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001131 self.mod(mod, msg, exc=exc)
1132
1133 def stmt(self, stmt, msg=None):
Guido van Rossumdcfcd142019-01-31 03:40:27 -08001134 mod = ast.Module([stmt], [])
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001135 self.mod(mod, msg)
1136
1137 def test_module(self):
1138 m = ast.Interactive([ast.Expr(ast.Name("x", ast.Store()))])
1139 self.mod(m, "must have Load context", "single")
1140 m = ast.Expression(ast.Name("x", ast.Store()))
1141 self.mod(m, "must have Load context", "eval")
1142
1143 def _check_arguments(self, fac, check):
Pablo Galindo8c77b8c2019-04-29 13:36:57 +01001144 def arguments(args=None, posonlyargs=None, vararg=None,
Benjamin Petersoncda75be2013-03-18 10:48:58 -07001145 kwonlyargs=None, kwarg=None,
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001146 defaults=None, kw_defaults=None):
1147 if args is None:
1148 args = []
Pablo Galindo8c77b8c2019-04-29 13:36:57 +01001149 if posonlyargs is None:
1150 posonlyargs = []
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001151 if kwonlyargs is None:
1152 kwonlyargs = []
1153 if defaults is None:
1154 defaults = []
1155 if kw_defaults is None:
1156 kw_defaults = []
Pablo Galindo8c77b8c2019-04-29 13:36:57 +01001157 args = ast.arguments(args, posonlyargs, vararg, kwonlyargs,
1158 kw_defaults, kwarg, defaults)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001159 return fac(args)
1160 args = [ast.arg("x", ast.Name("x", ast.Store()))]
1161 check(arguments(args=args), "must have Load context")
Pablo Galindo8c77b8c2019-04-29 13:36:57 +01001162 check(arguments(posonlyargs=args), "must have Load context")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001163 check(arguments(kwonlyargs=args), "must have Load context")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001164 check(arguments(defaults=[ast.Num(3)]),
1165 "more positional defaults than args")
1166 check(arguments(kw_defaults=[ast.Num(4)]),
1167 "length of kwonlyargs is not the same as kw_defaults")
1168 args = [ast.arg("x", ast.Name("x", ast.Load()))]
1169 check(arguments(args=args, defaults=[ast.Name("x", ast.Store())]),
1170 "must have Load context")
1171 args = [ast.arg("a", ast.Name("x", ast.Load())),
1172 ast.arg("b", ast.Name("y", ast.Load()))]
1173 check(arguments(kwonlyargs=args,
1174 kw_defaults=[None, ast.Name("x", ast.Store())]),
1175 "must have Load context")
1176
1177 def test_funcdef(self):
Pablo Galindo8c77b8c2019-04-29 13:36:57 +01001178 a = ast.arguments([], [], None, [], [], None, [])
Serhiy Storchaka73cbe7a2018-05-29 12:04:55 +03001179 f = ast.FunctionDef("x", a, [], [], None)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001180 self.stmt(f, "empty body on FunctionDef")
1181 f = ast.FunctionDef("x", a, [ast.Pass()], [ast.Name("x", ast.Store())],
Serhiy Storchaka73cbe7a2018-05-29 12:04:55 +03001182 None)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001183 self.stmt(f, "must have Load context")
1184 f = ast.FunctionDef("x", a, [ast.Pass()], [],
Serhiy Storchaka73cbe7a2018-05-29 12:04:55 +03001185 ast.Name("x", ast.Store()))
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001186 self.stmt(f, "must have Load context")
1187 def fac(args):
Serhiy Storchaka73cbe7a2018-05-29 12:04:55 +03001188 return ast.FunctionDef("x", args, [ast.Pass()], [], None)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001189 self._check_arguments(fac, self.stmt)
1190
1191 def test_classdef(self):
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04001192 def cls(bases=None, keywords=None, body=None, decorator_list=None):
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001193 if bases is None:
1194 bases = []
1195 if keywords is None:
1196 keywords = []
1197 if body is None:
1198 body = [ast.Pass()]
1199 if decorator_list is None:
1200 decorator_list = []
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04001201 return ast.ClassDef("myclass", bases, keywords,
Serhiy Storchaka73cbe7a2018-05-29 12:04:55 +03001202 body, decorator_list)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001203 self.stmt(cls(bases=[ast.Name("x", ast.Store())]),
1204 "must have Load context")
1205 self.stmt(cls(keywords=[ast.keyword("x", ast.Name("x", ast.Store()))]),
1206 "must have Load context")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001207 self.stmt(cls(body=[]), "empty body on ClassDef")
1208 self.stmt(cls(body=[None]), "None disallowed")
1209 self.stmt(cls(decorator_list=[ast.Name("x", ast.Store())]),
1210 "must have Load context")
1211
1212 def test_delete(self):
1213 self.stmt(ast.Delete([]), "empty targets on Delete")
1214 self.stmt(ast.Delete([None]), "None disallowed")
1215 self.stmt(ast.Delete([ast.Name("x", ast.Load())]),
1216 "must have Del context")
1217
1218 def test_assign(self):
1219 self.stmt(ast.Assign([], ast.Num(3)), "empty targets on Assign")
1220 self.stmt(ast.Assign([None], ast.Num(3)), "None disallowed")
1221 self.stmt(ast.Assign([ast.Name("x", ast.Load())], ast.Num(3)),
1222 "must have Store context")
1223 self.stmt(ast.Assign([ast.Name("x", ast.Store())],
1224 ast.Name("y", ast.Store())),
1225 "must have Load context")
1226
1227 def test_augassign(self):
1228 aug = ast.AugAssign(ast.Name("x", ast.Load()), ast.Add(),
1229 ast.Name("y", ast.Load()))
1230 self.stmt(aug, "must have Store context")
1231 aug = ast.AugAssign(ast.Name("x", ast.Store()), ast.Add(),
1232 ast.Name("y", ast.Store()))
1233 self.stmt(aug, "must have Load context")
1234
1235 def test_for(self):
1236 x = ast.Name("x", ast.Store())
1237 y = ast.Name("y", ast.Load())
1238 p = ast.Pass()
1239 self.stmt(ast.For(x, y, [], []), "empty body on For")
1240 self.stmt(ast.For(ast.Name("x", ast.Load()), y, [p], []),
1241 "must have Store context")
1242 self.stmt(ast.For(x, ast.Name("y", ast.Store()), [p], []),
1243 "must have Load context")
1244 e = ast.Expr(ast.Name("x", ast.Store()))
1245 self.stmt(ast.For(x, y, [e], []), "must have Load context")
1246 self.stmt(ast.For(x, y, [p], [e]), "must have Load context")
1247
1248 def test_while(self):
1249 self.stmt(ast.While(ast.Num(3), [], []), "empty body on While")
1250 self.stmt(ast.While(ast.Name("x", ast.Store()), [ast.Pass()], []),
1251 "must have Load context")
1252 self.stmt(ast.While(ast.Num(3), [ast.Pass()],
1253 [ast.Expr(ast.Name("x", ast.Store()))]),
1254 "must have Load context")
1255
1256 def test_if(self):
1257 self.stmt(ast.If(ast.Num(3), [], []), "empty body on If")
1258 i = ast.If(ast.Name("x", ast.Store()), [ast.Pass()], [])
1259 self.stmt(i, "must have Load context")
1260 i = ast.If(ast.Num(3), [ast.Expr(ast.Name("x", ast.Store()))], [])
1261 self.stmt(i, "must have Load context")
1262 i = ast.If(ast.Num(3), [ast.Pass()],
1263 [ast.Expr(ast.Name("x", ast.Store()))])
1264 self.stmt(i, "must have Load context")
1265
1266 def test_with(self):
1267 p = ast.Pass()
1268 self.stmt(ast.With([], [p]), "empty items on With")
1269 i = ast.withitem(ast.Num(3), None)
1270 self.stmt(ast.With([i], []), "empty body on With")
1271 i = ast.withitem(ast.Name("x", ast.Store()), None)
1272 self.stmt(ast.With([i], [p]), "must have Load context")
1273 i = ast.withitem(ast.Num(3), ast.Name("x", ast.Load()))
1274 self.stmt(ast.With([i], [p]), "must have Store context")
1275
1276 def test_raise(self):
1277 r = ast.Raise(None, ast.Num(3))
1278 self.stmt(r, "Raise with cause but no exception")
1279 r = ast.Raise(ast.Name("x", ast.Store()), None)
1280 self.stmt(r, "must have Load context")
1281 r = ast.Raise(ast.Num(4), ast.Name("x", ast.Store()))
1282 self.stmt(r, "must have Load context")
1283
1284 def test_try(self):
1285 p = ast.Pass()
1286 t = ast.Try([], [], [], [p])
1287 self.stmt(t, "empty body on Try")
1288 t = ast.Try([ast.Expr(ast.Name("x", ast.Store()))], [], [], [p])
1289 self.stmt(t, "must have Load context")
1290 t = ast.Try([p], [], [], [])
1291 self.stmt(t, "Try has neither except handlers nor finalbody")
1292 t = ast.Try([p], [], [p], [p])
1293 self.stmt(t, "Try has orelse but no except handlers")
1294 t = ast.Try([p], [ast.ExceptHandler(None, "x", [])], [], [])
1295 self.stmt(t, "empty body on ExceptHandler")
1296 e = [ast.ExceptHandler(ast.Name("x", ast.Store()), "y", [p])]
1297 self.stmt(ast.Try([p], e, [], []), "must have Load context")
1298 e = [ast.ExceptHandler(None, "x", [p])]
1299 t = ast.Try([p], e, [ast.Expr(ast.Name("x", ast.Store()))], [p])
1300 self.stmt(t, "must have Load context")
1301 t = ast.Try([p], e, [p], [ast.Expr(ast.Name("x", ast.Store()))])
1302 self.stmt(t, "must have Load context")
1303
1304 def test_assert(self):
1305 self.stmt(ast.Assert(ast.Name("x", ast.Store()), None),
1306 "must have Load context")
1307 assrt = ast.Assert(ast.Name("x", ast.Load()),
1308 ast.Name("y", ast.Store()))
1309 self.stmt(assrt, "must have Load context")
1310
1311 def test_import(self):
1312 self.stmt(ast.Import([]), "empty names on Import")
1313
1314 def test_importfrom(self):
1315 imp = ast.ImportFrom(None, [ast.alias("x", None)], -42)
Serhiy Storchaka7de28402016-06-27 23:40:43 +03001316 self.stmt(imp, "Negative ImportFrom level")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001317 self.stmt(ast.ImportFrom(None, [], 0), "empty names on ImportFrom")
1318
1319 def test_global(self):
1320 self.stmt(ast.Global([]), "empty names on Global")
1321
1322 def test_nonlocal(self):
1323 self.stmt(ast.Nonlocal([]), "empty names on Nonlocal")
1324
1325 def test_expr(self):
1326 e = ast.Expr(ast.Name("x", ast.Store()))
1327 self.stmt(e, "must have Load context")
1328
1329 def test_boolop(self):
1330 b = ast.BoolOp(ast.And(), [])
1331 self.expr(b, "less than 2 values")
1332 b = ast.BoolOp(ast.And(), [ast.Num(3)])
1333 self.expr(b, "less than 2 values")
1334 b = ast.BoolOp(ast.And(), [ast.Num(4), None])
1335 self.expr(b, "None disallowed")
1336 b = ast.BoolOp(ast.And(), [ast.Num(4), ast.Name("x", ast.Store())])
1337 self.expr(b, "must have Load context")
1338
1339 def test_unaryop(self):
1340 u = ast.UnaryOp(ast.Not(), ast.Name("x", ast.Store()))
1341 self.expr(u, "must have Load context")
1342
1343 def test_lambda(self):
Pablo Galindo8c77b8c2019-04-29 13:36:57 +01001344 a = ast.arguments([], [], None, [], [], None, [])
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001345 self.expr(ast.Lambda(a, ast.Name("x", ast.Store())),
1346 "must have Load context")
1347 def fac(args):
1348 return ast.Lambda(args, ast.Name("x", ast.Load()))
1349 self._check_arguments(fac, self.expr)
1350
1351 def test_ifexp(self):
1352 l = ast.Name("x", ast.Load())
1353 s = ast.Name("y", ast.Store())
1354 for args in (s, l, l), (l, s, l), (l, l, s):
Benjamin Peterson71ce8972011-08-09 16:17:12 -05001355 self.expr(ast.IfExp(*args), "must have Load context")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001356
1357 def test_dict(self):
1358 d = ast.Dict([], [ast.Name("x", ast.Load())])
1359 self.expr(d, "same number of keys as values")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001360 d = ast.Dict([ast.Name("x", ast.Load())], [None])
1361 self.expr(d, "None disallowed")
1362
1363 def test_set(self):
1364 self.expr(ast.Set([None]), "None disallowed")
1365 s = ast.Set([ast.Name("x", ast.Store())])
1366 self.expr(s, "must have Load context")
1367
1368 def _check_comprehension(self, fac):
1369 self.expr(fac([]), "comprehension with no generators")
1370 g = ast.comprehension(ast.Name("x", ast.Load()),
Yury Selivanov52c4e7c2016-09-09 10:36:01 -07001371 ast.Name("x", ast.Load()), [], 0)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001372 self.expr(fac([g]), "must have Store context")
1373 g = ast.comprehension(ast.Name("x", ast.Store()),
Yury Selivanov52c4e7c2016-09-09 10:36:01 -07001374 ast.Name("x", ast.Store()), [], 0)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001375 self.expr(fac([g]), "must have Load context")
1376 x = ast.Name("x", ast.Store())
1377 y = ast.Name("y", ast.Load())
Yury Selivanov52c4e7c2016-09-09 10:36:01 -07001378 g = ast.comprehension(x, y, [None], 0)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001379 self.expr(fac([g]), "None disallowed")
Yury Selivanov52c4e7c2016-09-09 10:36:01 -07001380 g = ast.comprehension(x, y, [ast.Name("x", ast.Store())], 0)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001381 self.expr(fac([g]), "must have Load context")
1382
1383 def _simple_comp(self, fac):
1384 g = ast.comprehension(ast.Name("x", ast.Store()),
Yury Selivanov52c4e7c2016-09-09 10:36:01 -07001385 ast.Name("x", ast.Load()), [], 0)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001386 self.expr(fac(ast.Name("x", ast.Store()), [g]),
1387 "must have Load context")
1388 def wrap(gens):
1389 return fac(ast.Name("x", ast.Store()), gens)
1390 self._check_comprehension(wrap)
1391
1392 def test_listcomp(self):
1393 self._simple_comp(ast.ListComp)
1394
1395 def test_setcomp(self):
1396 self._simple_comp(ast.SetComp)
1397
1398 def test_generatorexp(self):
1399 self._simple_comp(ast.GeneratorExp)
1400
1401 def test_dictcomp(self):
1402 g = ast.comprehension(ast.Name("y", ast.Store()),
Yury Selivanov52c4e7c2016-09-09 10:36:01 -07001403 ast.Name("p", ast.Load()), [], 0)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001404 c = ast.DictComp(ast.Name("x", ast.Store()),
1405 ast.Name("y", ast.Load()), [g])
1406 self.expr(c, "must have Load context")
1407 c = ast.DictComp(ast.Name("x", ast.Load()),
1408 ast.Name("y", ast.Store()), [g])
1409 self.expr(c, "must have Load context")
1410 def factory(comps):
1411 k = ast.Name("x", ast.Load())
1412 v = ast.Name("y", ast.Load())
1413 return ast.DictComp(k, v, comps)
1414 self._check_comprehension(factory)
1415
1416 def test_yield(self):
Benjamin Peterson527c6222012-01-14 08:58:23 -05001417 self.expr(ast.Yield(ast.Name("x", ast.Store())), "must have Load")
1418 self.expr(ast.YieldFrom(ast.Name("x", ast.Store())), "must have Load")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001419
1420 def test_compare(self):
1421 left = ast.Name("x", ast.Load())
1422 comp = ast.Compare(left, [ast.In()], [])
1423 self.expr(comp, "no comparators")
1424 comp = ast.Compare(left, [ast.In()], [ast.Num(4), ast.Num(5)])
1425 self.expr(comp, "different number of comparators and operands")
1426 comp = ast.Compare(ast.Num("blah"), [ast.In()], [left])
Serhiy Storchaka3f228112018-09-27 17:42:37 +03001427 self.expr(comp)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001428 comp = ast.Compare(left, [ast.In()], [ast.Num("blah")])
Serhiy Storchaka3f228112018-09-27 17:42:37 +03001429 self.expr(comp)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001430
1431 def test_call(self):
1432 func = ast.Name("x", ast.Load())
1433 args = [ast.Name("y", ast.Load())]
1434 keywords = [ast.keyword("w", ast.Name("z", ast.Load()))]
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04001435 call = ast.Call(ast.Name("x", ast.Store()), args, keywords)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001436 self.expr(call, "must have Load context")
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04001437 call = ast.Call(func, [None], keywords)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001438 self.expr(call, "None disallowed")
1439 bad_keywords = [ast.keyword("w", ast.Name("z", ast.Store()))]
Benjamin Peterson025e9eb2015-05-05 20:16:41 -04001440 call = ast.Call(func, args, bad_keywords)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001441 self.expr(call, "must have Load context")
1442
1443 def test_num(self):
1444 class subint(int):
1445 pass
1446 class subfloat(float):
1447 pass
1448 class subcomplex(complex):
1449 pass
Serhiy Storchaka3f228112018-09-27 17:42:37 +03001450 for obj in "0", "hello":
1451 self.expr(ast.Num(obj))
1452 for obj in subint(), subfloat(), subcomplex():
1453 self.expr(ast.Num(obj), "invalid type", exc=TypeError)
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001454
1455 def test_attribute(self):
1456 attr = ast.Attribute(ast.Name("x", ast.Store()), "y", ast.Load())
1457 self.expr(attr, "must have Load context")
1458
1459 def test_subscript(self):
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02001460 sub = ast.Subscript(ast.Name("x", ast.Store()), ast.Num(3),
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001461 ast.Load())
1462 self.expr(sub, "must have Load context")
1463 x = ast.Name("x", ast.Load())
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02001464 sub = ast.Subscript(x, ast.Name("y", ast.Store()),
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001465 ast.Load())
1466 self.expr(sub, "must have Load context")
1467 s = ast.Name("x", ast.Store())
1468 for args in (s, None, None), (None, s, None), (None, None, s):
1469 sl = ast.Slice(*args)
1470 self.expr(ast.Subscript(x, sl, ast.Load()),
1471 "must have Load context")
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02001472 sl = ast.Tuple([], ast.Load())
1473 self.expr(ast.Subscript(x, sl, ast.Load()))
1474 sl = ast.Tuple([s], ast.Load())
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001475 self.expr(ast.Subscript(x, sl, ast.Load()), "must have Load context")
1476
1477 def test_starred(self):
1478 left = ast.List([ast.Starred(ast.Name("x", ast.Load()), ast.Store())],
1479 ast.Store())
1480 assign = ast.Assign([left], ast.Num(4))
1481 self.stmt(assign, "must have Store context")
1482
1483 def _sequence(self, fac):
1484 self.expr(fac([None], ast.Load()), "None disallowed")
1485 self.expr(fac([ast.Name("x", ast.Store())], ast.Load()),
1486 "must have Load context")
1487
1488 def test_list(self):
1489 self._sequence(ast.List)
1490
1491 def test_tuple(self):
1492 self._sequence(ast.Tuple)
1493
Benjamin Peterson442f2092012-12-06 17:41:04 -05001494 def test_nameconstant(self):
Serhiy Storchaka3f228112018-09-27 17:42:37 +03001495 self.expr(ast.NameConstant(4))
Benjamin Peterson442f2092012-12-06 17:41:04 -05001496
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001497 def test_stdlib_validates(self):
1498 stdlib = os.path.dirname(ast.__file__)
1499 tests = [fn for fn in os.listdir(stdlib) if fn.endswith(".py")]
1500 tests.extend(["test/test_grammar.py", "test/test_unpack_ex.py"])
1501 for module in tests:
Serhiy Storchaka3bcbedc2019-01-18 07:47:48 +02001502 with self.subTest(module):
1503 fn = os.path.join(stdlib, module)
1504 with open(fn, "r", encoding="utf-8") as fp:
1505 source = fp.read()
1506 mod = ast.parse(source, fn)
1507 compile(mod, fn, "exec")
Benjamin Peterson832bfe22011-08-09 16:15:04 -05001508
1509
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001510class ConstantTests(unittest.TestCase):
1511 """Tests on the ast.Constant node type."""
1512
1513 def compile_constant(self, value):
1514 tree = ast.parse("x = 123")
1515
1516 node = tree.body[0].value
1517 new_node = ast.Constant(value=value)
1518 ast.copy_location(new_node, node)
1519 tree.body[0].value = new_node
1520
1521 code = compile(tree, "<string>", "exec")
1522
1523 ns = {}
1524 exec(code, ns)
1525 return ns['x']
1526
Victor Stinnerbe59d142016-01-27 00:39:12 +01001527 def test_validation(self):
1528 with self.assertRaises(TypeError) as cm:
1529 self.compile_constant([1, 2, 3])
1530 self.assertEqual(str(cm.exception),
1531 "got an invalid type in Constant: list")
1532
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001533 def test_singletons(self):
1534 for const in (None, False, True, Ellipsis, b'', frozenset()):
1535 with self.subTest(const=const):
1536 value = self.compile_constant(const)
1537 self.assertIs(value, const)
1538
1539 def test_values(self):
1540 nested_tuple = (1,)
1541 nested_frozenset = frozenset({1})
1542 for level in range(3):
1543 nested_tuple = (nested_tuple, 2)
1544 nested_frozenset = frozenset({nested_frozenset, 2})
1545 values = (123, 123.0, 123j,
1546 "unicode", b'bytes',
1547 tuple("tuple"), frozenset("frozenset"),
1548 nested_tuple, nested_frozenset)
1549 for value in values:
1550 with self.subTest(value=value):
1551 result = self.compile_constant(value)
1552 self.assertEqual(result, value)
1553
1554 def test_assign_to_constant(self):
1555 tree = ast.parse("x = 1")
1556
1557 target = tree.body[0].targets[0]
1558 new_target = ast.Constant(value=1)
1559 ast.copy_location(new_target, target)
1560 tree.body[0].targets[0] = new_target
1561
1562 with self.assertRaises(ValueError) as cm:
1563 compile(tree, "string", "exec")
1564 self.assertEqual(str(cm.exception),
1565 "expression which can't be assigned "
1566 "to in Store context")
1567
1568 def test_get_docstring(self):
1569 tree = ast.parse("'docstring'\nx = 1")
1570 self.assertEqual(ast.get_docstring(tree), 'docstring')
1571
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001572 def get_load_const(self, tree):
1573 # Compile to bytecode, disassemble and get parameter of LOAD_CONST
1574 # instructions
1575 co = compile(tree, '<string>', 'exec')
1576 consts = []
1577 for instr in dis.get_instructions(co):
1578 if instr.opname == 'LOAD_CONST':
1579 consts.append(instr.argval)
1580 return consts
1581
1582 @support.cpython_only
1583 def test_load_const(self):
1584 consts = [None,
1585 True, False,
1586 124,
1587 2.0,
1588 3j,
1589 "unicode",
1590 b'bytes',
1591 (1, 2, 3)]
1592
Victor Stinnera2724092016-02-08 18:17:58 +01001593 code = '\n'.join(['x={!r}'.format(const) for const in consts])
1594 code += '\nx = ...'
1595 consts.extend((Ellipsis, None))
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001596
1597 tree = ast.parse(code)
Victor Stinnera2724092016-02-08 18:17:58 +01001598 self.assertEqual(self.get_load_const(tree),
1599 consts)
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001600
1601 # Replace expression nodes with constants
Victor Stinnera2724092016-02-08 18:17:58 +01001602 for assign, const in zip(tree.body, consts):
1603 assert isinstance(assign, ast.Assign), ast.dump(assign)
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001604 new_node = ast.Constant(value=const)
Victor Stinnera2724092016-02-08 18:17:58 +01001605 ast.copy_location(new_node, assign.value)
1606 assign.value = new_node
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001607
Victor Stinnera2724092016-02-08 18:17:58 +01001608 self.assertEqual(self.get_load_const(tree),
1609 consts)
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001610
1611 def test_literal_eval(self):
1612 tree = ast.parse("1 + 2")
1613 binop = tree.body[0].value
1614
1615 new_left = ast.Constant(value=10)
1616 ast.copy_location(new_left, binop.left)
1617 binop.left = new_left
1618
Serhiy Storchakad8ac4d12018-01-04 11:15:39 +02001619 new_right = ast.Constant(value=20j)
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001620 ast.copy_location(new_right, binop.right)
1621 binop.right = new_right
1622
Serhiy Storchakad8ac4d12018-01-04 11:15:39 +02001623 self.assertEqual(ast.literal_eval(binop), 10+20j)
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001624
Guido van Rossum10f8ce62019-03-13 13:00:46 -07001625 def test_string_kind(self):
1626 c = ast.parse('"x"', mode='eval').body
1627 self.assertEqual(c.value, "x")
1628 self.assertEqual(c.kind, None)
1629
1630 c = ast.parse('u"x"', mode='eval').body
1631 self.assertEqual(c.value, "x")
1632 self.assertEqual(c.kind, "u")
1633
1634 c = ast.parse('r"x"', mode='eval').body
1635 self.assertEqual(c.value, "x")
1636 self.assertEqual(c.kind, None)
1637
1638 c = ast.parse('b"x"', mode='eval').body
1639 self.assertEqual(c.value, b"x")
1640 self.assertEqual(c.kind, None)
1641
Victor Stinnerf2c1aa12016-01-26 00:40:57 +01001642
Ivan Levkivskyi9932a222019-01-22 11:18:22 +00001643class EndPositionTests(unittest.TestCase):
1644 """Tests for end position of AST nodes.
1645
1646 Testing end positions of nodes requires a bit of extra care
1647 because of how LL parsers work.
1648 """
1649 def _check_end_pos(self, ast_node, end_lineno, end_col_offset):
1650 self.assertEqual(ast_node.end_lineno, end_lineno)
1651 self.assertEqual(ast_node.end_col_offset, end_col_offset)
1652
1653 def _check_content(self, source, ast_node, content):
1654 self.assertEqual(ast.get_source_segment(source, ast_node), content)
1655
1656 def _parse_value(self, s):
1657 # Use duck-typing to support both single expression
1658 # and a right hand side of an assignment statement.
1659 return ast.parse(s).body[0].value
1660
1661 def test_lambda(self):
1662 s = 'lambda x, *y: None'
1663 lam = self._parse_value(s)
1664 self._check_content(s, lam.body, 'None')
1665 self._check_content(s, lam.args.args[0], 'x')
1666 self._check_content(s, lam.args.vararg, 'y')
1667
1668 def test_func_def(self):
1669 s = dedent('''
1670 def func(x: int,
1671 *args: str,
1672 z: float = 0,
1673 **kwargs: Any) -> bool:
1674 return True
1675 ''').strip()
1676 fdef = ast.parse(s).body[0]
1677 self._check_end_pos(fdef, 5, 15)
1678 self._check_content(s, fdef.body[0], 'return True')
1679 self._check_content(s, fdef.args.args[0], 'x: int')
1680 self._check_content(s, fdef.args.args[0].annotation, 'int')
1681 self._check_content(s, fdef.args.kwarg, 'kwargs: Any')
1682 self._check_content(s, fdef.args.kwarg.annotation, 'Any')
1683
1684 def test_call(self):
1685 s = 'func(x, y=2, **kw)'
1686 call = self._parse_value(s)
1687 self._check_content(s, call.func, 'func')
1688 self._check_content(s, call.keywords[0].value, '2')
1689 self._check_content(s, call.keywords[1].value, 'kw')
1690
1691 def test_call_noargs(self):
1692 s = 'x[0]()'
1693 call = self._parse_value(s)
1694 self._check_content(s, call.func, 'x[0]')
1695 self._check_end_pos(call, 1, 6)
1696
1697 def test_class_def(self):
1698 s = dedent('''
1699 class C(A, B):
1700 x: int = 0
1701 ''').strip()
1702 cdef = ast.parse(s).body[0]
1703 self._check_end_pos(cdef, 2, 14)
1704 self._check_content(s, cdef.bases[1], 'B')
1705 self._check_content(s, cdef.body[0], 'x: int = 0')
1706
1707 def test_class_kw(self):
1708 s = 'class S(metaclass=abc.ABCMeta): pass'
1709 cdef = ast.parse(s).body[0]
1710 self._check_content(s, cdef.keywords[0].value, 'abc.ABCMeta')
1711
1712 def test_multi_line_str(self):
1713 s = dedent('''
1714 x = """Some multi-line text.
1715
1716 It goes on starting from same indent."""
1717 ''').strip()
1718 assign = ast.parse(s).body[0]
1719 self._check_end_pos(assign, 3, 40)
1720 self._check_end_pos(assign.value, 3, 40)
1721
1722 def test_continued_str(self):
1723 s = dedent('''
1724 x = "first part" \\
1725 "second part"
1726 ''').strip()
1727 assign = ast.parse(s).body[0]
1728 self._check_end_pos(assign, 2, 13)
1729 self._check_end_pos(assign.value, 2, 13)
1730
1731 def test_suites(self):
1732 # We intentionally put these into the same string to check
1733 # that empty lines are not part of the suite.
1734 s = dedent('''
1735 while True:
1736 pass
1737
1738 if one():
1739 x = None
1740 elif other():
1741 y = None
1742 else:
1743 z = None
1744
1745 for x, y in stuff:
1746 assert True
1747
1748 try:
1749 raise RuntimeError
1750 except TypeError as e:
1751 pass
1752
1753 pass
1754 ''').strip()
1755 mod = ast.parse(s)
1756 while_loop = mod.body[0]
1757 if_stmt = mod.body[1]
1758 for_loop = mod.body[2]
1759 try_stmt = mod.body[3]
1760 pass_stmt = mod.body[4]
1761
1762 self._check_end_pos(while_loop, 2, 8)
1763 self._check_end_pos(if_stmt, 9, 12)
1764 self._check_end_pos(for_loop, 12, 15)
1765 self._check_end_pos(try_stmt, 17, 8)
1766 self._check_end_pos(pass_stmt, 19, 4)
1767
1768 self._check_content(s, while_loop.test, 'True')
1769 self._check_content(s, if_stmt.body[0], 'x = None')
1770 self._check_content(s, if_stmt.orelse[0].test, 'other()')
1771 self._check_content(s, for_loop.target, 'x, y')
1772 self._check_content(s, try_stmt.body[0], 'raise RuntimeError')
1773 self._check_content(s, try_stmt.handlers[0].type, 'TypeError')
1774
1775 def test_fstring(self):
1776 s = 'x = f"abc {x + y} abc"'
1777 fstr = self._parse_value(s)
1778 binop = fstr.values[1].value
1779 self._check_content(s, binop, 'x + y')
1780
1781 def test_fstring_multi_line(self):
1782 s = dedent('''
1783 f"""Some multi-line text.
1784 {
1785 arg_one
1786 +
1787 arg_two
1788 }
1789 It goes on..."""
1790 ''').strip()
1791 fstr = self._parse_value(s)
1792 binop = fstr.values[1].value
1793 self._check_end_pos(binop, 5, 7)
1794 self._check_content(s, binop.left, 'arg_one')
1795 self._check_content(s, binop.right, 'arg_two')
1796
1797 def test_import_from_multi_line(self):
1798 s = dedent('''
1799 from x.y.z import (
1800 a, b, c as c
1801 )
1802 ''').strip()
1803 imp = ast.parse(s).body[0]
1804 self._check_end_pos(imp, 3, 1)
Matthew Suozzo75a06f02021-04-10 16:56:28 -04001805 self._check_end_pos(imp.names[2], 2, 16)
Ivan Levkivskyi9932a222019-01-22 11:18:22 +00001806
1807 def test_slices(self):
1808 s1 = 'f()[1, 2] [0]'
1809 s2 = 'x[ a.b: c.d]'
1810 sm = dedent('''
1811 x[ a.b: f () ,
1812 g () : c.d
1813 ]
1814 ''').strip()
1815 i1, i2, im = map(self._parse_value, (s1, s2, sm))
1816 self._check_content(s1, i1.value, 'f()[1, 2]')
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02001817 self._check_content(s1, i1.value.slice, '1, 2')
Ivan Levkivskyi9932a222019-01-22 11:18:22 +00001818 self._check_content(s2, i2.slice.lower, 'a.b')
1819 self._check_content(s2, i2.slice.upper, 'c.d')
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02001820 self._check_content(sm, im.slice.elts[0].upper, 'f ()')
1821 self._check_content(sm, im.slice.elts[1].lower, 'g ()')
Ivan Levkivskyi9932a222019-01-22 11:18:22 +00001822 self._check_end_pos(im, 3, 3)
1823
1824 def test_binop(self):
1825 s = dedent('''
1826 (1 * 2 + (3 ) +
1827 4
1828 )
1829 ''').strip()
1830 binop = self._parse_value(s)
1831 self._check_end_pos(binop, 2, 6)
1832 self._check_content(s, binop.right, '4')
1833 self._check_content(s, binop.left, '1 * 2 + (3 )')
1834 self._check_content(s, binop.left.right, '3')
1835
1836 def test_boolop(self):
1837 s = dedent('''
1838 if (one_condition and
1839 (other_condition or yet_another_one)):
1840 pass
1841 ''').strip()
1842 bop = ast.parse(s).body[0].test
1843 self._check_end_pos(bop, 2, 44)
1844 self._check_content(s, bop.values[1],
1845 'other_condition or yet_another_one')
1846
1847 def test_tuples(self):
1848 s1 = 'x = () ;'
1849 s2 = 'x = 1 , ;'
1850 s3 = 'x = (1 , 2 ) ;'
1851 sm = dedent('''
1852 x = (
1853 a, b,
1854 )
1855 ''').strip()
1856 t1, t2, t3, tm = map(self._parse_value, (s1, s2, s3, sm))
1857 self._check_content(s1, t1, '()')
1858 self._check_content(s2, t2, '1 ,')
1859 self._check_content(s3, t3, '(1 , 2 )')
1860 self._check_end_pos(tm, 3, 1)
1861
1862 def test_attribute_spaces(self):
1863 s = 'func(x. y .z)'
1864 call = self._parse_value(s)
1865 self._check_content(s, call, s)
1866 self._check_content(s, call.args[0], 'x. y .z')
1867
Serhiy Storchaka6e619c42020-02-12 22:37:49 +02001868 def test_redundant_parenthesis(self):
1869 s = '( ( ( a + b ) ) )'
1870 v = ast.parse(s).body[0].value
1871 self.assertEqual(type(v).__name__, 'BinOp')
1872 self._check_content(s, v, 'a + b')
1873 s2 = 'await ' + s
1874 v = ast.parse(s2).body[0].value.value
1875 self.assertEqual(type(v).__name__, 'BinOp')
1876 self._check_content(s2, v, 'a + b')
1877
1878 def test_trailers_with_redundant_parenthesis(self):
1879 tests = (
1880 ('( ( ( a ) ) ) ( )', 'Call'),
1881 ('( ( ( a ) ) ) ( b )', 'Call'),
1882 ('( ( ( a ) ) ) [ b ]', 'Subscript'),
1883 ('( ( ( a ) ) ) . b', 'Attribute'),
1884 )
1885 for s, t in tests:
1886 with self.subTest(s):
1887 v = ast.parse(s).body[0].value
1888 self.assertEqual(type(v).__name__, t)
1889 self._check_content(s, v, s)
1890 s2 = 'await ' + s
1891 v = ast.parse(s2).body[0].value.value
1892 self.assertEqual(type(v).__name__, t)
1893 self._check_content(s2, v, s)
1894
Ivan Levkivskyi9932a222019-01-22 11:18:22 +00001895 def test_displays(self):
1896 s1 = '[{}, {1, }, {1, 2,} ]'
1897 s2 = '{a: b, f (): g () ,}'
1898 c1 = self._parse_value(s1)
1899 c2 = self._parse_value(s2)
1900 self._check_content(s1, c1.elts[0], '{}')
1901 self._check_content(s1, c1.elts[1], '{1, }')
1902 self._check_content(s1, c1.elts[2], '{1, 2,}')
1903 self._check_content(s2, c2.keys[1], 'f ()')
1904 self._check_content(s2, c2.values[1], 'g ()')
1905
1906 def test_comprehensions(self):
1907 s = dedent('''
1908 x = [{x for x, y in stuff
1909 if cond.x} for stuff in things]
1910 ''').strip()
1911 cmp = self._parse_value(s)
1912 self._check_end_pos(cmp, 2, 37)
1913 self._check_content(s, cmp.generators[0].iter, 'things')
1914 self._check_content(s, cmp.elt.generators[0].iter, 'stuff')
1915 self._check_content(s, cmp.elt.generators[0].ifs[0], 'cond.x')
1916 self._check_content(s, cmp.elt.generators[0].target, 'x, y')
1917
1918 def test_yield_await(self):
1919 s = dedent('''
1920 async def f():
1921 yield x
1922 await y
1923 ''').strip()
1924 fdef = ast.parse(s).body[0]
1925 self._check_content(s, fdef.body[0].value, 'yield x')
1926 self._check_content(s, fdef.body[1].value, 'await y')
1927
1928 def test_source_segment_multi(self):
1929 s_orig = dedent('''
1930 x = (
1931 a, b,
1932 ) + ()
1933 ''').strip()
1934 s_tuple = dedent('''
1935 (
1936 a, b,
1937 )
1938 ''').strip()
1939 binop = self._parse_value(s_orig)
1940 self.assertEqual(ast.get_source_segment(s_orig, binop.left), s_tuple)
1941
1942 def test_source_segment_padded(self):
1943 s_orig = dedent('''
1944 class C:
1945 def fun(self) -> None:
1946 "Đ–Đ–Đ–Đ–Đ–"
1947 ''').strip()
1948 s_method = ' def fun(self) -> None:\n' \
1949 ' "Đ–Đ–Đ–Đ–Đ–"'
1950 cdef = ast.parse(s_orig).body[0]
1951 self.assertEqual(ast.get_source_segment(s_orig, cdef.body[0], padded=True),
1952 s_method)
1953
1954 def test_source_segment_endings(self):
1955 s = 'v = 1\r\nw = 1\nx = 1\n\ry = 1\rz = 1\r\n'
1956 v, w, x, y, z = ast.parse(s).body
1957 self._check_content(s, v, 'v = 1')
1958 self._check_content(s, w, 'w = 1')
1959 self._check_content(s, x, 'x = 1')
1960 self._check_content(s, y, 'y = 1')
1961 self._check_content(s, z, 'z = 1')
1962
1963 def test_source_segment_tabs(self):
1964 s = dedent('''
1965 class C:
1966 \t\f def fun(self) -> None:
1967 \t\f pass
1968 ''').strip()
1969 s_method = ' \t\f def fun(self) -> None:\n' \
1970 ' \t\f pass'
1971
1972 cdef = ast.parse(s).body[0]
1973 self.assertEqual(ast.get_source_segment(s, cdef.body[0], padded=True), s_method)
1974
Irit Katriele6578a22020-05-18 19:14:12 +01001975 def test_source_segment_missing_info(self):
1976 s = 'v = 1\r\nw = 1\nx = 1\n\ry = 1\r\n'
1977 v, w, x, y = ast.parse(s).body
1978 del v.lineno
1979 del w.end_lineno
1980 del x.col_offset
1981 del y.end_col_offset
1982 self.assertIsNone(ast.get_source_segment(s, v))
1983 self.assertIsNone(ast.get_source_segment(s, w))
1984 self.assertIsNone(ast.get_source_segment(s, x))
1985 self.assertIsNone(ast.get_source_segment(s, y))
Ivan Levkivskyi9932a222019-01-22 11:18:22 +00001986
Serhiy Storchakac3ea41e2019-08-26 10:13:19 +03001987class NodeVisitorTests(unittest.TestCase):
1988 def test_old_constant_nodes(self):
1989 class Visitor(ast.NodeVisitor):
1990 def visit_Num(self, node):
1991 log.append((node.lineno, 'Num', node.n))
1992 def visit_Str(self, node):
1993 log.append((node.lineno, 'Str', node.s))
1994 def visit_Bytes(self, node):
1995 log.append((node.lineno, 'Bytes', node.s))
1996 def visit_NameConstant(self, node):
1997 log.append((node.lineno, 'NameConstant', node.value))
1998 def visit_Ellipsis(self, node):
1999 log.append((node.lineno, 'Ellipsis', ...))
2000 mod = ast.parse(dedent('''\
2001 i = 42
2002 f = 4.25
2003 c = 4.25j
2004 s = 'string'
2005 b = b'bytes'
2006 t = True
2007 n = None
2008 e = ...
2009 '''))
2010 visitor = Visitor()
2011 log = []
2012 with warnings.catch_warnings(record=True) as wlog:
2013 warnings.filterwarnings('always', '', DeprecationWarning)
2014 visitor.visit(mod)
2015 self.assertEqual(log, [
2016 (1, 'Num', 42),
2017 (2, 'Num', 4.25),
2018 (3, 'Num', 4.25j),
2019 (4, 'Str', 'string'),
2020 (5, 'Bytes', b'bytes'),
2021 (6, 'NameConstant', True),
2022 (7, 'NameConstant', None),
2023 (8, 'Ellipsis', ...),
2024 ])
2025 self.assertEqual([str(w.message) for w in wlog], [
2026 'visit_Num is deprecated; add visit_Constant',
2027 'visit_Num is deprecated; add visit_Constant',
2028 'visit_Num is deprecated; add visit_Constant',
2029 'visit_Str is deprecated; add visit_Constant',
2030 'visit_Bytes is deprecated; add visit_Constant',
2031 'visit_NameConstant is deprecated; add visit_Constant',
2032 'visit_NameConstant is deprecated; add visit_Constant',
2033 'visit_Ellipsis is deprecated; add visit_Constant',
2034 ])
2035
2036
Victor Stinnere5fbe0c2020-09-15 18:03:34 +02002037@support.cpython_only
2038class ModuleStateTests(unittest.TestCase):
2039 # bpo-41194, bpo-41261, bpo-41631: The _ast module uses a global state.
2040
2041 def check_ast_module(self):
2042 # Check that the _ast module still works as expected
2043 code = 'x + 1'
2044 filename = '<string>'
2045 mode = 'eval'
2046
2047 # Create _ast.AST subclasses instances
2048 ast_tree = compile(code, filename, mode, flags=ast.PyCF_ONLY_AST)
2049
2050 # Call PyAST_Check()
2051 code = compile(ast_tree, filename, mode)
2052 self.assertIsInstance(code, types.CodeType)
2053
2054 def test_reload_module(self):
2055 # bpo-41194: Importing the _ast module twice must not crash.
2056 with support.swap_item(sys.modules, '_ast', None):
2057 del sys.modules['_ast']
2058 import _ast as ast1
2059
2060 del sys.modules['_ast']
2061 import _ast as ast2
2062
2063 self.check_ast_module()
2064
2065 # Unloading the two _ast module instances must not crash.
2066 del ast1
2067 del ast2
2068 support.gc_collect()
2069
2070 self.check_ast_module()
2071
2072 def test_sys_modules(self):
2073 # bpo-41631: Test reproducing a Mercurial crash when PyAST_Check()
2074 # imported the _ast module internally.
2075 lazy_mod = object()
2076
2077 def my_import(name, *args, **kw):
2078 sys.modules[name] = lazy_mod
2079 return lazy_mod
2080
2081 with support.swap_item(sys.modules, '_ast', None):
2082 del sys.modules['_ast']
2083
2084 with support.swap_attr(builtins, '__import__', my_import):
2085 # Test that compile() does not import the _ast module
2086 self.check_ast_module()
2087 self.assertNotIn('_ast', sys.modules)
2088
2089 # Sanity check of the test itself
2090 import _ast
2091 self.assertIs(_ast, lazy_mod)
2092
2093 def test_subinterpreter(self):
2094 # bpo-41631: Importing and using the _ast module in a subinterpreter
2095 # must not crash.
2096 code = dedent('''
2097 import _ast
2098 import ast
2099 import gc
2100 import sys
2101 import types
2102
2103 # Create _ast.AST subclasses instances and call PyAST_Check()
2104 ast_tree = compile('x+1', '<string>', 'eval',
2105 flags=ast.PyCF_ONLY_AST)
2106 code = compile(ast_tree, 'string', 'eval')
2107 if not isinstance(code, types.CodeType):
2108 raise AssertionError
2109
2110 # Unloading the _ast module must not crash.
2111 del ast, _ast
2112 del sys.modules['ast'], sys.modules['_ast']
2113 gc.collect()
2114 ''')
2115 res = support.run_in_subinterp(code)
2116 self.assertEqual(res, 0)
2117
2118
Neal Norwitzee9b10a2008-03-31 05:29:39 +00002119def main():
2120 if __name__ != '__main__':
Martin v. Löwis49c5da12006-03-01 22:49:05 +00002121 return
Neal Norwitzee9b10a2008-03-31 05:29:39 +00002122 if sys.argv[1:] == ['-g']:
2123 for statements, kind in ((exec_tests, "exec"), (single_tests, "single"),
2124 (eval_tests, "eval")):
2125 print(kind+"_results = [")
Victor Stinnerf0891962016-02-08 17:15:21 +01002126 for statement in statements:
2127 tree = ast.parse(statement, "?", kind)
2128 print("%r," % (to_tuple(tree),))
Neal Norwitzee9b10a2008-03-31 05:29:39 +00002129 print("]")
2130 print("main()")
2131 raise SystemExit
Brett Cannon3e9a9ae2013-06-12 21:25:59 -04002132 unittest.main()
Tim Peters400cbc32006-02-28 18:44:41 +00002133
Guido van Rossumdcfcd142019-01-31 03:40:27 -08002134#### EVERYTHING BELOW IS GENERATED BY python Lib/test/test_ast.py -g #####
Tim Peters400cbc32006-02-28 18:44:41 +00002135exec_results = [
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002136('Module', [('Expr', (1, 0, 1, 4), ('Constant', (1, 0, 1, 4), None, None))], []),
2137('Module', [('Expr', (1, 0, 1, 18), ('Constant', (1, 0, 1, 18), 'module docstring', None))], []),
2138('Module', [('FunctionDef', (1, 0, 1, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (1, 9, 1, 13))], [], None, None)], []),
2139('Module', [('FunctionDef', (1, 0, 1, 29), 'f', ('arguments', [], [], None, [], [], None, []), [('Expr', (1, 9, 1, 29), ('Constant', (1, 9, 1, 29), 'function docstring', None))], [], None, None)], []),
2140('Module', [('FunctionDef', (1, 0, 1, 14), 'f', ('arguments', [], [('arg', (1, 6, 1, 7), 'a', None, None)], None, [], [], None, []), [('Pass', (1, 10, 1, 14))], [], None, None)], []),
2141('Module', [('FunctionDef', (1, 0, 1, 16), 'f', ('arguments', [], [('arg', (1, 6, 1, 7), 'a', None, None)], None, [], [], None, [('Constant', (1, 8, 1, 9), 0, None)]), [('Pass', (1, 12, 1, 16))], [], None, None)], []),
2142('Module', [('FunctionDef', (1, 0, 1, 18), 'f', ('arguments', [], [], ('arg', (1, 7, 1, 11), 'args', None, None), [], [], None, []), [('Pass', (1, 14, 1, 18))], [], None, None)], []),
2143('Module', [('FunctionDef', (1, 0, 1, 21), 'f', ('arguments', [], [], None, [], [], ('arg', (1, 8, 1, 14), 'kwargs', None, None), []), [('Pass', (1, 17, 1, 21))], [], None, None)], []),
2144('Module', [('FunctionDef', (1, 0, 1, 71), 'f', ('arguments', [], [('arg', (1, 6, 1, 7), 'a', None, None), ('arg', (1, 9, 1, 10), 'b', None, None), ('arg', (1, 14, 1, 15), 'c', None, None), ('arg', (1, 22, 1, 23), 'd', None, None), ('arg', (1, 28, 1, 29), 'e', None, None)], ('arg', (1, 35, 1, 39), 'args', None, None), [('arg', (1, 41, 1, 42), 'f', None, None)], [('Constant', (1, 43, 1, 45), 42, None)], ('arg', (1, 49, 1, 55), 'kwargs', None, None), [('Constant', (1, 11, 1, 12), 1, None), ('Constant', (1, 16, 1, 20), None, None), ('List', (1, 24, 1, 26), [], ('Load',)), ('Dict', (1, 30, 1, 32), [], [])]), [('Expr', (1, 58, 1, 71), ('Constant', (1, 58, 1, 71), 'doc for f()', None))], [], None, None)], []),
2145('Module', [('ClassDef', (1, 0, 1, 12), 'C', [], [], [('Pass', (1, 8, 1, 12))], [])], []),
2146('Module', [('ClassDef', (1, 0, 1, 32), 'C', [], [], [('Expr', (1, 9, 1, 32), ('Constant', (1, 9, 1, 32), 'docstring for class C', None))], [])], []),
2147('Module', [('ClassDef', (1, 0, 1, 21), 'C', [('Name', (1, 8, 1, 14), 'object', ('Load',))], [], [('Pass', (1, 17, 1, 21))], [])], []),
2148('Module', [('FunctionDef', (1, 0, 1, 16), 'f', ('arguments', [], [], None, [], [], None, []), [('Return', (1, 8, 1, 16), ('Constant', (1, 15, 1, 16), 1, None))], [], None, None)], []),
2149('Module', [('Delete', (1, 0, 1, 5), [('Name', (1, 4, 1, 5), 'v', ('Del',))])], []),
2150('Module', [('Assign', (1, 0, 1, 5), [('Name', (1, 0, 1, 1), 'v', ('Store',))], ('Constant', (1, 4, 1, 5), 1, None), None)], []),
2151('Module', [('Assign', (1, 0, 1, 7), [('Tuple', (1, 0, 1, 3), [('Name', (1, 0, 1, 1), 'a', ('Store',)), ('Name', (1, 2, 1, 3), 'b', ('Store',))], ('Store',))], ('Name', (1, 6, 1, 7), 'c', ('Load',)), None)], []),
2152('Module', [('Assign', (1, 0, 1, 9), [('Tuple', (1, 0, 1, 5), [('Name', (1, 1, 1, 2), 'a', ('Store',)), ('Name', (1, 3, 1, 4), 'b', ('Store',))], ('Store',))], ('Name', (1, 8, 1, 9), 'c', ('Load',)), None)], []),
2153('Module', [('Assign', (1, 0, 1, 9), [('List', (1, 0, 1, 5), [('Name', (1, 1, 1, 2), 'a', ('Store',)), ('Name', (1, 3, 1, 4), 'b', ('Store',))], ('Store',))], ('Name', (1, 8, 1, 9), 'c', ('Load',)), None)], []),
2154('Module', [('AugAssign', (1, 0, 1, 6), ('Name', (1, 0, 1, 1), 'v', ('Store',)), ('Add',), ('Constant', (1, 5, 1, 6), 1, None))], []),
2155('Module', [('For', (1, 0, 1, 15), ('Name', (1, 4, 1, 5), 'v', ('Store',)), ('Name', (1, 9, 1, 10), 'v', ('Load',)), [('Pass', (1, 11, 1, 15))], [], None)], []),
2156('Module', [('While', (1, 0, 1, 12), ('Name', (1, 6, 1, 7), 'v', ('Load',)), [('Pass', (1, 8, 1, 12))], [])], []),
2157('Module', [('If', (1, 0, 1, 9), ('Name', (1, 3, 1, 4), 'v', ('Load',)), [('Pass', (1, 5, 1, 9))], [])], []),
2158('Module', [('If', (1, 0, 4, 6), ('Name', (1, 3, 1, 4), 'a', ('Load',)), [('Pass', (2, 2, 2, 6))], [('If', (3, 0, 4, 6), ('Name', (3, 5, 3, 6), 'b', ('Load',)), [('Pass', (4, 2, 4, 6))], [])])], []),
2159('Module', [('If', (1, 0, 6, 6), ('Name', (1, 3, 1, 4), 'a', ('Load',)), [('Pass', (2, 2, 2, 6))], [('If', (3, 0, 6, 6), ('Name', (3, 5, 3, 6), 'b', ('Load',)), [('Pass', (4, 2, 4, 6))], [('Pass', (6, 2, 6, 6))])])], []),
2160('Module', [('With', (1, 0, 1, 17), [('withitem', ('Name', (1, 5, 1, 6), 'x', ('Load',)), ('Name', (1, 10, 1, 11), 'y', ('Store',)))], [('Pass', (1, 13, 1, 17))], None)], []),
2161('Module', [('With', (1, 0, 1, 25), [('withitem', ('Name', (1, 5, 1, 6), 'x', ('Load',)), ('Name', (1, 10, 1, 11), 'y', ('Store',))), ('withitem', ('Name', (1, 13, 1, 14), 'z', ('Load',)), ('Name', (1, 18, 1, 19), 'q', ('Store',)))], [('Pass', (1, 21, 1, 25))], None)], []),
2162('Module', [('Raise', (1, 0, 1, 25), ('Call', (1, 6, 1, 25), ('Name', (1, 6, 1, 15), 'Exception', ('Load',)), [('Constant', (1, 16, 1, 24), 'string', None)], []), None)], []),
2163('Module', [('Try', (1, 0, 4, 6), [('Pass', (2, 2, 2, 6))], [('ExceptHandler', (3, 0, 4, 6), ('Name', (3, 7, 3, 16), 'Exception', ('Load',)), None, [('Pass', (4, 2, 4, 6))])], [], [])], []),
2164('Module', [('Try', (1, 0, 4, 6), [('Pass', (2, 2, 2, 6))], [], [], [('Pass', (4, 2, 4, 6))])], []),
2165('Module', [('Assert', (1, 0, 1, 8), ('Name', (1, 7, 1, 8), 'v', ('Load',)), None)], []),
Matthew Suozzo75a06f02021-04-10 16:56:28 -04002166('Module', [('Import', (1, 0, 1, 10), [('alias', (1, 7, 1, 10), 'sys', None)])], []),
2167('Module', [('ImportFrom', (1, 0, 1, 17), 'sys', [('alias', (1, 16, 1, 17), 'v', None)], 0)], []),
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002168('Module', [('Global', (1, 0, 1, 8), ['v'])], []),
2169('Module', [('Expr', (1, 0, 1, 1), ('Constant', (1, 0, 1, 1), 1, None))], []),
2170('Module', [('Pass', (1, 0, 1, 4))], []),
2171('Module', [('For', (1, 0, 1, 16), ('Name', (1, 4, 1, 5), 'v', ('Store',)), ('Name', (1, 9, 1, 10), 'v', ('Load',)), [('Break', (1, 11, 1, 16))], [], None)], []),
2172('Module', [('For', (1, 0, 1, 19), ('Name', (1, 4, 1, 5), 'v', ('Store',)), ('Name', (1, 9, 1, 10), 'v', ('Load',)), [('Continue', (1, 11, 1, 19))], [], None)], []),
2173('Module', [('For', (1, 0, 1, 18), ('Tuple', (1, 4, 1, 7), [('Name', (1, 4, 1, 5), 'a', ('Store',)), ('Name', (1, 6, 1, 7), 'b', ('Store',))], ('Store',)), ('Name', (1, 11, 1, 12), 'c', ('Load',)), [('Pass', (1, 14, 1, 18))], [], None)], []),
2174('Module', [('For', (1, 0, 1, 20), ('Tuple', (1, 4, 1, 9), [('Name', (1, 5, 1, 6), 'a', ('Store',)), ('Name', (1, 7, 1, 8), 'b', ('Store',))], ('Store',)), ('Name', (1, 13, 1, 14), 'c', ('Load',)), [('Pass', (1, 16, 1, 20))], [], None)], []),
2175('Module', [('For', (1, 0, 1, 20), ('List', (1, 4, 1, 9), [('Name', (1, 5, 1, 6), 'a', ('Store',)), ('Name', (1, 7, 1, 8), 'b', ('Store',))], ('Store',)), ('Name', (1, 13, 1, 14), 'c', ('Load',)), [('Pass', (1, 16, 1, 20))], [], None)], []),
2176('Module', [('Expr', (1, 0, 11, 5), ('GeneratorExp', (1, 0, 11, 5), ('Tuple', (2, 4, 6, 5), [('Name', (3, 4, 3, 6), 'Aa', ('Load',)), ('Name', (5, 7, 5, 9), 'Bb', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (8, 4, 10, 6), [('Name', (8, 4, 8, 6), 'Aa', ('Store',)), ('Name', (10, 4, 10, 6), 'Bb', ('Store',))], ('Store',)), ('Name', (10, 10, 10, 12), 'Cc', ('Load',)), [], 0)]))], []),
2177('Module', [('Expr', (1, 0, 1, 34), ('DictComp', (1, 0, 1, 34), ('Name', (1, 1, 1, 2), 'a', ('Load',)), ('Name', (1, 5, 1, 6), 'b', ('Load',)), [('comprehension', ('Name', (1, 11, 1, 12), 'w', ('Store',)), ('Name', (1, 16, 1, 17), 'x', ('Load',)), [], 0), ('comprehension', ('Name', (1, 22, 1, 23), 'm', ('Store',)), ('Name', (1, 27, 1, 28), 'p', ('Load',)), [('Name', (1, 32, 1, 33), 'g', ('Load',))], 0)]))], []),
2178('Module', [('Expr', (1, 0, 1, 20), ('DictComp', (1, 0, 1, 20), ('Name', (1, 1, 1, 2), 'a', ('Load',)), ('Name', (1, 5, 1, 6), 'b', ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'v', ('Store',)), ('Name', (1, 13, 1, 14), 'w', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'x', ('Load',)), [], 0)]))], []),
2179('Module', [('Expr', (1, 0, 1, 19), ('SetComp', (1, 0, 1, 19), ('Name', (1, 1, 1, 2), 'r', ('Load',)), [('comprehension', ('Name', (1, 7, 1, 8), 'l', ('Store',)), ('Name', (1, 12, 1, 13), 'x', ('Load',)), [('Name', (1, 17, 1, 18), 'g', ('Load',))], 0)]))], []),
2180('Module', [('Expr', (1, 0, 1, 16), ('SetComp', (1, 0, 1, 16), ('Name', (1, 1, 1, 2), 'r', ('Load',)), [('comprehension', ('Tuple', (1, 7, 1, 10), [('Name', (1, 7, 1, 8), 'l', ('Store',)), ('Name', (1, 9, 1, 10), 'm', ('Store',))], ('Store',)), ('Name', (1, 14, 1, 15), 'x', ('Load',)), [], 0)]))], []),
2181('Module', [('AsyncFunctionDef', (1, 0, 3, 18), 'f', ('arguments', [], [], None, [], [], None, []), [('Expr', (2, 1, 2, 17), ('Constant', (2, 1, 2, 17), 'async function', None)), ('Expr', (3, 1, 3, 18), ('Await', (3, 1, 3, 18), ('Call', (3, 7, 3, 18), ('Name', (3, 7, 3, 16), 'something', ('Load',)), [], [])))], [], None, None)], []),
2182('Module', [('AsyncFunctionDef', (1, 0, 3, 8), 'f', ('arguments', [], [], None, [], [], None, []), [('AsyncFor', (2, 1, 3, 8), ('Name', (2, 11, 2, 12), 'e', ('Store',)), ('Name', (2, 16, 2, 17), 'i', ('Load',)), [('Expr', (2, 19, 2, 20), ('Constant', (2, 19, 2, 20), 1, None))], [('Expr', (3, 7, 3, 8), ('Constant', (3, 7, 3, 8), 2, None))], None)], [], None, None)], []),
2183('Module', [('AsyncFunctionDef', (1, 0, 2, 21), 'f', ('arguments', [], [], None, [], [], None, []), [('AsyncWith', (2, 1, 2, 21), [('withitem', ('Name', (2, 12, 2, 13), 'a', ('Load',)), ('Name', (2, 17, 2, 18), 'b', ('Store',)))], [('Expr', (2, 20, 2, 21), ('Constant', (2, 20, 2, 21), 1, None))], None)], [], None, None)], []),
2184('Module', [('Expr', (1, 0, 1, 14), ('Dict', (1, 0, 1, 14), [None, ('Constant', (1, 10, 1, 11), 2, None)], [('Dict', (1, 3, 1, 8), [('Constant', (1, 4, 1, 5), 1, None)], [('Constant', (1, 6, 1, 7), 2, None)]), ('Constant', (1, 12, 1, 13), 3, None)]))], []),
2185('Module', [('Expr', (1, 0, 1, 12), ('Set', (1, 0, 1, 12), [('Starred', (1, 1, 1, 8), ('Set', (1, 2, 1, 8), [('Constant', (1, 3, 1, 4), 1, None), ('Constant', (1, 6, 1, 7), 2, None)]), ('Load',)), ('Constant', (1, 10, 1, 11), 3, None)]))], []),
2186('Module', [('AsyncFunctionDef', (1, 0, 2, 21), 'f', ('arguments', [], [], None, [], [], None, []), [('Expr', (2, 1, 2, 21), ('ListComp', (2, 1, 2, 21), ('Name', (2, 2, 2, 3), 'i', ('Load',)), [('comprehension', ('Name', (2, 14, 2, 15), 'b', ('Store',)), ('Name', (2, 19, 2, 20), 'c', ('Load',)), [], 1)]))], [], None, None)], []),
2187('Module', [('FunctionDef', (4, 0, 4, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (4, 9, 4, 13))], [('Name', (1, 1, 1, 6), 'deco1', ('Load',)), ('Call', (2, 1, 2, 8), ('Name', (2, 1, 2, 6), 'deco2', ('Load',)), [], []), ('Call', (3, 1, 3, 9), ('Name', (3, 1, 3, 6), 'deco3', ('Load',)), [('Constant', (3, 7, 3, 8), 1, None)], [])], None, None)], []),
2188('Module', [('AsyncFunctionDef', (4, 0, 4, 19), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (4, 15, 4, 19))], [('Name', (1, 1, 1, 6), 'deco1', ('Load',)), ('Call', (2, 1, 2, 8), ('Name', (2, 1, 2, 6), 'deco2', ('Load',)), [], []), ('Call', (3, 1, 3, 9), ('Name', (3, 1, 3, 6), 'deco3', ('Load',)), [('Constant', (3, 7, 3, 8), 1, None)], [])], None, None)], []),
2189('Module', [('ClassDef', (4, 0, 4, 13), 'C', [], [], [('Pass', (4, 9, 4, 13))], [('Name', (1, 1, 1, 6), 'deco1', ('Load',)), ('Call', (2, 1, 2, 8), ('Name', (2, 1, 2, 6), 'deco2', ('Load',)), [], []), ('Call', (3, 1, 3, 9), ('Name', (3, 1, 3, 6), 'deco3', ('Load',)), [('Constant', (3, 7, 3, 8), 1, None)], [])])], []),
2190('Module', [('FunctionDef', (2, 0, 2, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (2, 9, 2, 13))], [('Call', (1, 1, 1, 19), ('Name', (1, 1, 1, 5), 'deco', ('Load',)), [('GeneratorExp', (1, 5, 1, 19), ('Name', (1, 6, 1, 7), 'a', ('Load',)), [('comprehension', ('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 17, 1, 18), 'b', ('Load',)), [], 0)])], [])], None, None)], []),
Lysandros Nikolaoud2e10982020-02-08 00:36:32 +01002191('Module', [('FunctionDef', (2, 0, 2, 13), 'f', ('arguments', [], [], None, [], [], None, []), [('Pass', (2, 9, 2, 13))], [('Attribute', (1, 1, 1, 6), ('Attribute', (1, 1, 1, 4), ('Name', (1, 1, 1, 2), 'a', ('Load',)), 'b', ('Load',)), 'c', ('Load',))], None, None)], []),
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002192('Module', [('Expr', (1, 0, 1, 8), ('NamedExpr', (1, 1, 1, 7), ('Name', (1, 1, 1, 2), 'a', ('Store',)), ('Constant', (1, 6, 1, 7), 1, None)))], []),
2193('Module', [('FunctionDef', (1, 0, 1, 18), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [], None, [], [], None, []), [('Pass', (1, 14, 1, 18))], [], None, None)], []),
2194('Module', [('FunctionDef', (1, 0, 1, 26), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 12, 1, 13), 'c', None, None), ('arg', (1, 15, 1, 16), 'd', None, None), ('arg', (1, 18, 1, 19), 'e', None, None)], None, [], [], None, []), [('Pass', (1, 22, 1, 26))], [], None, None)], []),
2195('Module', [('FunctionDef', (1, 0, 1, 29), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 12, 1, 13), 'c', None, None)], None, [('arg', (1, 18, 1, 19), 'd', None, None), ('arg', (1, 21, 1, 22), 'e', None, None)], [None, None], None, []), [('Pass', (1, 25, 1, 29))], [], None, None)], []),
2196('Module', [('FunctionDef', (1, 0, 1, 39), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 12, 1, 13), 'c', None, None)], None, [('arg', (1, 18, 1, 19), 'd', None, None), ('arg', (1, 21, 1, 22), 'e', None, None)], [None, None], ('arg', (1, 26, 1, 32), 'kwargs', None, None), []), [('Pass', (1, 35, 1, 39))], [], None, None)], []),
2197('Module', [('FunctionDef', (1, 0, 1, 20), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [], None, [], [], None, [('Constant', (1, 8, 1, 9), 1, None)]), [('Pass', (1, 16, 1, 20))], [], None, None)], []),
2198('Module', [('FunctionDef', (1, 0, 1, 29), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None), ('arg', (1, 19, 1, 20), 'c', None, None)], None, [], [], None, [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None), ('Constant', (1, 21, 1, 22), 4, None)]), [('Pass', (1, 25, 1, 29))], [], None, None)], []),
2199('Module', [('FunctionDef', (1, 0, 1, 32), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [('Constant', (1, 24, 1, 25), 4, None)], None, [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 28, 1, 32))], [], None, None)], []),
2200('Module', [('FunctionDef', (1, 0, 1, 30), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [None], None, [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 26, 1, 30))], [], None, None)], []),
2201('Module', [('FunctionDef', (1, 0, 1, 42), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [('Constant', (1, 24, 1, 25), 4, None)], ('arg', (1, 29, 1, 35), 'kwargs', None, None), [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 38, 1, 42))], [], None, None)], []),
2202('Module', [('FunctionDef', (1, 0, 1, 40), 'f', ('arguments', [('arg', (1, 6, 1, 7), 'a', None, None)], [('arg', (1, 14, 1, 15), 'b', None, None)], None, [('arg', (1, 22, 1, 23), 'c', None, None)], [None], ('arg', (1, 27, 1, 33), 'kwargs', None, None), [('Constant', (1, 8, 1, 9), 1, None), ('Constant', (1, 16, 1, 17), 2, None)]), [('Pass', (1, 36, 1, 40))], [], None, None)], []),
Tim Peters400cbc32006-02-28 18:44:41 +00002203]
2204single_results = [
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002205('Interactive', [('Expr', (1, 0, 1, 3), ('BinOp', (1, 0, 1, 3), ('Constant', (1, 0, 1, 1), 1, None), ('Add',), ('Constant', (1, 2, 1, 3), 2, None)))]),
Tim Peters400cbc32006-02-28 18:44:41 +00002206]
2207eval_results = [
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002208('Expression', ('Constant', (1, 0, 1, 4), None, None)),
2209('Expression', ('BoolOp', (1, 0, 1, 7), ('And',), [('Name', (1, 0, 1, 1), 'a', ('Load',)), ('Name', (1, 6, 1, 7), 'b', ('Load',))])),
2210('Expression', ('BinOp', (1, 0, 1, 5), ('Name', (1, 0, 1, 1), 'a', ('Load',)), ('Add',), ('Name', (1, 4, 1, 5), 'b', ('Load',)))),
2211('Expression', ('UnaryOp', (1, 0, 1, 5), ('Not',), ('Name', (1, 4, 1, 5), 'v', ('Load',)))),
2212('Expression', ('Lambda', (1, 0, 1, 11), ('arguments', [], [], None, [], [], None, []), ('Constant', (1, 7, 1, 11), None, None))),
2213('Expression', ('Dict', (1, 0, 1, 7), [('Constant', (1, 2, 1, 3), 1, None)], [('Constant', (1, 4, 1, 5), 2, None)])),
2214('Expression', ('Dict', (1, 0, 1, 2), [], [])),
2215('Expression', ('Set', (1, 0, 1, 7), [('Constant', (1, 1, 1, 5), None, None)])),
2216('Expression', ('Dict', (1, 0, 5, 6), [('Constant', (2, 6, 2, 7), 1, None)], [('Constant', (4, 10, 4, 11), 2, None)])),
2217('Expression', ('ListComp', (1, 0, 1, 19), ('Name', (1, 1, 1, 2), 'a', ('Load',)), [('comprehension', ('Name', (1, 7, 1, 8), 'b', ('Store',)), ('Name', (1, 12, 1, 13), 'c', ('Load',)), [('Name', (1, 17, 1, 18), 'd', ('Load',))], 0)])),
2218('Expression', ('GeneratorExp', (1, 0, 1, 19), ('Name', (1, 1, 1, 2), 'a', ('Load',)), [('comprehension', ('Name', (1, 7, 1, 8), 'b', ('Store',)), ('Name', (1, 12, 1, 13), 'c', ('Load',)), [('Name', (1, 17, 1, 18), 'd', ('Load',))], 0)])),
2219('Expression', ('ListComp', (1, 0, 1, 20), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'c', ('Load',)), [], 0)])),
2220('Expression', ('ListComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2221('Expression', ('ListComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('List', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2222('Expression', ('SetComp', (1, 0, 1, 20), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'c', ('Load',)), [], 0)])),
2223('Expression', ('SetComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2224('Expression', ('SetComp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('List', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2225('Expression', ('GeneratorExp', (1, 0, 1, 20), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 14), [('Name', (1, 11, 1, 12), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Store',))], ('Store',)), ('Name', (1, 18, 1, 19), 'c', ('Load',)), [], 0)])),
2226('Expression', ('GeneratorExp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('Tuple', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2227('Expression', ('GeneratorExp', (1, 0, 1, 22), ('Tuple', (1, 1, 1, 6), [('Name', (1, 2, 1, 3), 'a', ('Load',)), ('Name', (1, 4, 1, 5), 'b', ('Load',))], ('Load',)), [('comprehension', ('List', (1, 11, 1, 16), [('Name', (1, 12, 1, 13), 'a', ('Store',)), ('Name', (1, 14, 1, 15), 'b', ('Store',))], ('Store',)), ('Name', (1, 20, 1, 21), 'c', ('Load',)), [], 0)])),
2228('Expression', ('Compare', (1, 0, 1, 9), ('Constant', (1, 0, 1, 1), 1, None), [('Lt',), ('Lt',)], [('Constant', (1, 4, 1, 5), 2, None), ('Constant', (1, 8, 1, 9), 3, None)])),
Pablo Galindo40cf35c2020-04-03 21:02:26 +01002229('Expression', ('Call', (1, 0, 1, 17), ('Name', (1, 0, 1, 1), 'f', ('Load',)), [('Constant', (1, 2, 1, 3), 1, None), ('Constant', (1, 4, 1, 5), 2, None), ('Starred', (1, 10, 1, 12), ('Name', (1, 11, 1, 12), 'd', ('Load',)), ('Load',))], [('keyword', (1, 6, 1, 9), 'c', ('Constant', (1, 8, 1, 9), 3, None)), ('keyword', (1, 13, 1, 16), None, ('Name', (1, 15, 1, 16), 'e', ('Load',)))])),
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002230('Expression', ('Call', (1, 0, 1, 10), ('Name', (1, 0, 1, 1), 'f', ('Load',)), [('Starred', (1, 2, 1, 9), ('List', (1, 3, 1, 9), [('Constant', (1, 4, 1, 5), 0, None), ('Constant', (1, 7, 1, 8), 1, None)], ('Load',)), ('Load',))], [])),
2231('Expression', ('Call', (1, 0, 1, 15), ('Name', (1, 0, 1, 1), 'f', ('Load',)), [('GeneratorExp', (1, 1, 1, 15), ('Name', (1, 2, 1, 3), 'a', ('Load',)), [('comprehension', ('Name', (1, 8, 1, 9), 'a', ('Store',)), ('Name', (1, 13, 1, 14), 'b', ('Load',)), [], 0)])], [])),
2232('Expression', ('Constant', (1, 0, 1, 2), 10, None)),
2233('Expression', ('Constant', (1, 0, 1, 8), 'string', None)),
2234('Expression', ('Attribute', (1, 0, 1, 3), ('Name', (1, 0, 1, 1), 'a', ('Load',)), 'b', ('Load',))),
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02002235('Expression', ('Subscript', (1, 0, 1, 6), ('Name', (1, 0, 1, 1), 'a', ('Load',)), ('Slice', (1, 2, 1, 5), ('Name', (1, 2, 1, 3), 'b', ('Load',)), ('Name', (1, 4, 1, 5), 'c', ('Load',)), None), ('Load',))),
Serhiy Storchaka850a8852020-01-10 10:12:55 +02002236('Expression', ('Name', (1, 0, 1, 1), 'v', ('Load',))),
2237('Expression', ('List', (1, 0, 1, 7), [('Constant', (1, 1, 1, 2), 1, None), ('Constant', (1, 3, 1, 4), 2, None), ('Constant', (1, 5, 1, 6), 3, None)], ('Load',))),
2238('Expression', ('List', (1, 0, 1, 2), [], ('Load',))),
2239('Expression', ('Tuple', (1, 0, 1, 5), [('Constant', (1, 0, 1, 1), 1, None), ('Constant', (1, 2, 1, 3), 2, None), ('Constant', (1, 4, 1, 5), 3, None)], ('Load',))),
2240('Expression', ('Tuple', (1, 0, 1, 7), [('Constant', (1, 1, 1, 2), 1, None), ('Constant', (1, 3, 1, 4), 2, None), ('Constant', (1, 5, 1, 6), 3, None)], ('Load',))),
2241('Expression', ('Tuple', (1, 0, 1, 2), [], ('Load',))),
Serhiy Storchaka13d52c22020-03-10 18:52:34 +02002242('Expression', ('Call', (1, 0, 1, 17), ('Attribute', (1, 0, 1, 7), ('Attribute', (1, 0, 1, 5), ('Attribute', (1, 0, 1, 3), ('Name', (1, 0, 1, 1), 'a', ('Load',)), 'b', ('Load',)), 'c', ('Load',)), 'd', ('Load',)), [('Subscript', (1, 8, 1, 16), ('Attribute', (1, 8, 1, 11), ('Name', (1, 8, 1, 9), 'a', ('Load',)), 'b', ('Load',)), ('Slice', (1, 12, 1, 15), ('Constant', (1, 12, 1, 13), 1, None), ('Constant', (1, 14, 1, 15), 2, None), None), ('Load',))], [])),
Tim Peters400cbc32006-02-28 18:44:41 +00002243]
Neal Norwitzee9b10a2008-03-31 05:29:39 +00002244main()