Fix some scripts in the peg generator folder (GH-19853)
This commit is contained in:
parent
02047265eb
commit
9dbaa8d9f0
|
@ -15,6 +15,7 @@ with test_tools.imports_under_tool("peg_generator"):
|
||||||
generate_parser_c_extension,
|
generate_parser_c_extension,
|
||||||
generate_c_parser_source,
|
generate_c_parser_source,
|
||||||
)
|
)
|
||||||
|
from pegen.ast_dump import ast_dump
|
||||||
|
|
||||||
|
|
||||||
TEST_TEMPLATE = """
|
TEST_TEMPLATE = """
|
||||||
|
@ -24,7 +25,10 @@ import ast
|
||||||
import traceback
|
import traceback
|
||||||
import sys
|
import sys
|
||||||
import unittest
|
import unittest
|
||||||
from test.test_peg_generator.ast_dump import ast_dump
|
|
||||||
|
from test import test_tools
|
||||||
|
with test_tools.imports_under_tool("peg_generator"):
|
||||||
|
from pegen.ast_dump import ast_dump
|
||||||
|
|
||||||
sys.path.insert(0, tmp_dir)
|
sys.path.insert(0, tmp_dir)
|
||||||
import parse
|
import parse
|
||||||
|
|
|
@ -7,4 +7,5 @@ if 1:
|
||||||
pass
|
pass
|
||||||
elif 1:
|
elif 1:
|
||||||
pass
|
pass
|
||||||
else: print("else-clause")
|
else:
|
||||||
|
print("else-clause")
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -6,16 +6,17 @@ always fail. We rely on string comparison of the base classes instead.
|
||||||
TODO: Remove the above-described hack.
|
TODO: Remove the above-described hack.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
||||||
def ast_dump(node, annotate_fields=True, include_attributes=False, *, indent=None):
|
def ast_dump(node, annotate_fields=True, include_attributes=False, *, indent=None):
|
||||||
def _format(node, level=0):
|
def _format(node, level=0):
|
||||||
if indent is not None:
|
if indent is not None:
|
||||||
level += 1
|
level += 1
|
||||||
prefix = '\n' + indent * level
|
prefix = "\n" + indent * level
|
||||||
sep = ',\n' + indent * level
|
sep = ",\n" + indent * level
|
||||||
else:
|
else:
|
||||||
prefix = ''
|
prefix = ""
|
||||||
sep = ', '
|
sep = ", "
|
||||||
if any(cls.__name__ == 'AST' for cls in node.__class__.__mro__):
|
if any(cls.__name__ == "AST" for cls in node.__class__.__mro__):
|
||||||
cls = type(node)
|
cls = type(node)
|
||||||
args = []
|
args = []
|
||||||
allsimple = True
|
allsimple = True
|
||||||
|
@ -32,7 +33,7 @@ def ast_dump(node, annotate_fields=True, include_attributes=False, *, indent=Non
|
||||||
value, simple = _format(value, level)
|
value, simple = _format(value, level)
|
||||||
allsimple = allsimple and simple
|
allsimple = allsimple and simple
|
||||||
if keywords:
|
if keywords:
|
||||||
args.append('%s=%s' % (name, value))
|
args.append("%s=%s" % (name, value))
|
||||||
else:
|
else:
|
||||||
args.append(value)
|
args.append(value)
|
||||||
if include_attributes and node._attributes:
|
if include_attributes and node._attributes:
|
||||||
|
@ -45,18 +46,18 @@ def ast_dump(node, annotate_fields=True, include_attributes=False, *, indent=Non
|
||||||
continue
|
continue
|
||||||
value, simple = _format(value, level)
|
value, simple = _format(value, level)
|
||||||
allsimple = allsimple and simple
|
allsimple = allsimple and simple
|
||||||
args.append('%s=%s' % (name, value))
|
args.append("%s=%s" % (name, value))
|
||||||
if allsimple and len(args) <= 3:
|
if allsimple and len(args) <= 3:
|
||||||
return '%s(%s)' % (node.__class__.__name__, ', '.join(args)), not args
|
return "%s(%s)" % (node.__class__.__name__, ", ".join(args)), not args
|
||||||
return '%s(%s%s)' % (node.__class__.__name__, prefix, sep.join(args)), False
|
return "%s(%s%s)" % (node.__class__.__name__, prefix, sep.join(args)), False
|
||||||
elif isinstance(node, list):
|
elif isinstance(node, list):
|
||||||
if not node:
|
if not node:
|
||||||
return '[]', True
|
return "[]", True
|
||||||
return '[%s%s]' % (prefix, sep.join(_format(x, level)[0] for x in node)), False
|
return "[%s%s]" % (prefix, sep.join(_format(x, level)[0] for x in node)), False
|
||||||
return repr(node), True
|
return repr(node), True
|
||||||
|
|
||||||
if all(cls.__name__ != 'AST' for cls in node.__class__.__mro__):
|
if all(cls.__name__ != "AST" for cls in node.__class__.__mro__):
|
||||||
raise TypeError('expected AST, got %r' % node.__class__.__name__)
|
raise TypeError("expected AST, got %r" % node.__class__.__name__)
|
||||||
if indent is not None and not isinstance(indent, str):
|
if indent is not None and not isinstance(indent, str):
|
||||||
indent = ' ' * indent
|
indent = " " * indent
|
||||||
return _format(node)[0]
|
return _format(node)[0]
|
|
@ -3,6 +3,7 @@ import shutil
|
||||||
import tokenize
|
import tokenize
|
||||||
import sys
|
import sys
|
||||||
import sysconfig
|
import sysconfig
|
||||||
|
import tempfile
|
||||||
import itertools
|
import itertools
|
||||||
|
|
||||||
from typing import Optional, Tuple, List, IO, Iterator, Set, Dict
|
from typing import Optional, Tuple, List, IO, Iterator, Set, Dict
|
||||||
|
@ -162,8 +163,12 @@ def build_c_generator(
|
||||||
gen.generate(grammar_file)
|
gen.generate(grammar_file)
|
||||||
|
|
||||||
if compile_extension:
|
if compile_extension:
|
||||||
|
with tempfile.TemporaryDirectory() as build_dir:
|
||||||
compile_c_extension(
|
compile_c_extension(
|
||||||
output_file, verbose=verbose_c_extension, keep_asserts=keep_asserts_in_extension
|
output_file,
|
||||||
|
build_dir=build_dir,
|
||||||
|
verbose=verbose_c_extension,
|
||||||
|
keep_asserts=keep_asserts_in_extension,
|
||||||
)
|
)
|
||||||
return gen
|
return gen
|
||||||
|
|
||||||
|
|
|
@ -105,10 +105,7 @@ def run_benchmark_stdlib(subcommand, parser):
|
||||||
"../../Lib",
|
"../../Lib",
|
||||||
"../../Grammar/python.gram",
|
"../../Grammar/python.gram",
|
||||||
verbose=False,
|
verbose=False,
|
||||||
excluded_files=[
|
excluded_files=["*/bad*", "*/lib2to3/tests/data/*",],
|
||||||
"*/bad*",
|
|
||||||
"*/lib2to3/tests/data/*",
|
|
||||||
],
|
|
||||||
skip_actions=False,
|
skip_actions=False,
|
||||||
tree_arg=0,
|
tree_arg=0,
|
||||||
short=True,
|
short=True,
|
||||||
|
|
|
@ -32,6 +32,9 @@ import tempfile
|
||||||
|
|
||||||
from typing import List
|
from typing import List
|
||||||
|
|
||||||
|
sys.path.insert(0, os.getcwd())
|
||||||
|
from pegen.ast_dump import ast_dump
|
||||||
|
|
||||||
parser = argparse.ArgumentParser()
|
parser = argparse.ArgumentParser()
|
||||||
parser.add_argument(
|
parser.add_argument(
|
||||||
"-d", "--diff", action="store_true", help="show diff between grammar and ast (requires -g)"
|
"-d", "--diff", action="store_true", help="show diff between grammar and ast (requires -g)"
|
||||||
|
@ -49,7 +52,7 @@ parser.add_argument("program", nargs="+", help="program to parse (will be concat
|
||||||
|
|
||||||
def format_tree(tree: ast.AST, verbose: bool = False) -> str:
|
def format_tree(tree: ast.AST, verbose: bool = False) -> str:
|
||||||
with tempfile.NamedTemporaryFile("w+") as tf:
|
with tempfile.NamedTemporaryFile("w+") as tf:
|
||||||
tf.write(ast.dump(tree, include_attributes=verbose))
|
tf.write(ast_dump(tree, include_attributes=verbose))
|
||||||
tf.write("\n")
|
tf.write("\n")
|
||||||
tf.flush()
|
tf.flush()
|
||||||
cmd = f"black -q {tf.name}"
|
cmd = f"black -q {tf.name}"
|
||||||
|
|
|
@ -14,6 +14,7 @@ from typing import List, Optional, Any
|
||||||
|
|
||||||
sys.path.insert(0, os.getcwd())
|
sys.path.insert(0, os.getcwd())
|
||||||
from pegen.build import build_c_parser_and_generator
|
from pegen.build import build_c_parser_and_generator
|
||||||
|
from pegen.ast_dump import ast_dump
|
||||||
from pegen.testutil import print_memstats
|
from pegen.testutil import print_memstats
|
||||||
from scripts import show_parse
|
from scripts import show_parse
|
||||||
|
|
||||||
|
@ -85,8 +86,8 @@ def compare_trees(
|
||||||
with open(file) as f:
|
with open(file) as f:
|
||||||
expected_tree = ast.parse(f.read())
|
expected_tree = ast.parse(f.read())
|
||||||
|
|
||||||
expected_text = ast.dump(expected_tree, include_attributes=include_attributes)
|
expected_text = ast_dump(expected_tree, include_attributes=include_attributes)
|
||||||
actual_text = ast.dump(actual_tree, include_attributes=include_attributes)
|
actual_text = ast_dump(actual_tree, include_attributes=include_attributes)
|
||||||
if actual_text == expected_text:
|
if actual_text == expected_text:
|
||||||
if verbose:
|
if verbose:
|
||||||
print("Tree for {file}:")
|
print("Tree for {file}:")
|
||||||
|
@ -164,7 +165,7 @@ def parse_directory(
|
||||||
if parser == "pegen":
|
if parser == "pegen":
|
||||||
try:
|
try:
|
||||||
from peg_extension import parse # type: ignore
|
from peg_extension import parse # type: ignore
|
||||||
except:
|
except Exception as e:
|
||||||
print(
|
print(
|
||||||
"An existing parser was not found. Please run `make` or specify a grammar file with the `-g` flag.",
|
"An existing parser was not found. Please run `make` or specify a grammar file with the `-g` flag.",
|
||||||
file=sys.stderr,
|
file=sys.stderr,
|
||||||
|
|
|
@ -6,14 +6,18 @@ import glob
|
||||||
import tarfile
|
import tarfile
|
||||||
import zipfile
|
import zipfile
|
||||||
import shutil
|
import shutil
|
||||||
|
import pathlib
|
||||||
import sys
|
import sys
|
||||||
|
|
||||||
from typing import Generator, Any
|
from typing import Generator, Any
|
||||||
|
|
||||||
sys.path.insert(0, ".")
|
sys.path.insert(0, ".")
|
||||||
|
|
||||||
from pegen import build
|
from pegen import build
|
||||||
from scripts import test_parse_directory
|
from scripts import test_parse_directory
|
||||||
|
|
||||||
|
HERE = pathlib.Path(__file__).resolve().parent
|
||||||
|
|
||||||
argparser = argparse.ArgumentParser(
|
argparser = argparse.ArgumentParser(
|
||||||
prog="test_pypi_packages", description="Helper program to test parsing PyPI packages",
|
prog="test_pypi_packages", description="Helper program to test parsing PyPI packages",
|
||||||
)
|
)
|
||||||
|
@ -53,7 +57,8 @@ def find_dirname(package_name: str) -> str:
|
||||||
def run_tests(dirname: str, tree: int, extension: Any) -> int:
|
def run_tests(dirname: str, tree: int, extension: Any) -> int:
|
||||||
return test_parse_directory.parse_directory(
|
return test_parse_directory.parse_directory(
|
||||||
dirname,
|
dirname,
|
||||||
"data/python.gram",
|
HERE / ".." / ".." / ".." / "Grammar" / "python.gram",
|
||||||
|
HERE / ".." / ".." / ".." / "Grammar" / "Tokens",
|
||||||
verbose=False,
|
verbose=False,
|
||||||
excluded_files=[
|
excluded_files=[
|
||||||
"*/failset/*",
|
"*/failset/*",
|
||||||
|
@ -68,6 +73,8 @@ def run_tests(dirname: str, tree: int, extension: Any) -> int:
|
||||||
tree_arg=tree,
|
tree_arg=tree,
|
||||||
short=True,
|
short=True,
|
||||||
extension=extension,
|
extension=extension,
|
||||||
|
mode=1,
|
||||||
|
parser="pegen",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@ -75,9 +82,13 @@ def main() -> None:
|
||||||
args = argparser.parse_args()
|
args = argparser.parse_args()
|
||||||
tree = args.tree
|
tree = args.tree
|
||||||
|
|
||||||
extension = build.build_parser_and_generator(
|
extension = build.build_c_parser_and_generator(
|
||||||
"data/python.gram", "peg_parser/parse.c", compile_extension=True
|
HERE / ".." / ".." / ".." / "Grammar" / "python.gram",
|
||||||
|
HERE / ".." / ".." / ".." / "Grammar" / "Tokens",
|
||||||
|
"peg_extension/parse.c",
|
||||||
|
compile_extension=True,
|
||||||
)
|
)
|
||||||
|
|
||||||
for package in get_packages():
|
for package in get_packages():
|
||||||
print(f"Extracting files from {package}... ", end="")
|
print(f"Extracting files from {package}... ", end="")
|
||||||
try:
|
try:
|
||||||
|
@ -91,7 +102,6 @@ def main() -> None:
|
||||||
dirname = find_dirname(package)
|
dirname = find_dirname(package)
|
||||||
status = run_tests(dirname, tree, extension)
|
status = run_tests(dirname, tree, extension)
|
||||||
if status == 0:
|
if status == 0:
|
||||||
print("Done")
|
|
||||||
shutil.rmtree(dirname)
|
shutil.rmtree(dirname)
|
||||||
else:
|
else:
|
||||||
print(f"Failed to parse {dirname}")
|
print(f"Failed to parse {dirname}")
|
||||||
|
|
Loading…
Reference in New Issue