From 1bfc91854a9d2b3d893c56487ab407ec8086251a Mon Sep 17 00:00:00 2001 From: Eric Brown Date: Tue, 23 Apr 2024 09:45:09 -0700 Subject: [PATCH] Fix traceback raised on an expression list assignment (#439) When there is an assignment using a pattern_list and expression_list, the current code will iterate through each assignment. However, the current code assumes it can use context['node'], which is not the expected node during the parse. ```console : Language(path, name) is deprecated. Use Language(ptr, name) instead. warn("{} is deprecated. Use {} instead.".format(old, new), FutureWarning) logging initialized Working on file: tests/unit/parsers/examples/expression_list_assignment.py Exception occurred when executing rules against tests/unit/parsers/examples/expression_list_assignment.py. Run "precli --debug tests/unit/parsers/examples/expression_list_assignment.py" to see the full traceback. Exception string: cannot access local variable 'func_node' where it is not associated with a value Exception traceback: Traceback (most recent call last): File "/Users/ericwb/workspace/precli/precli/core/run.py", line 127, in parse_file return parser.parse(artifact) ^^^^^^^^^^^^^^^^^^^^^^ File "/Users/ericwb/workspace/precli/precli/parsers/__init__.py", line 99, in parse self.visit([tree.root_node]) File "/Users/ericwb/workspace/precli/precli/parsers/__init__.py", line 124, in visit visitor_fn(node.children) File "/Users/ericwb/workspace/precli/precli/parsers/python.py", line 31, in visit_module self.visit(nodes) File "/Users/ericwb/workspace/precli/precli/parsers/__init__.py", line 124, in visit visitor_fn(node.children) File "/Users/ericwb/workspace/precli/precli/parsers/__init__.py", line 124, in visit visitor_fn(node.children) File "/Users/ericwb/workspace/precli/precli/parsers/python.py", line 98, in visit_assignment self.visit_assignment( File "/Users/ericwb/workspace/precli/precli/parsers/python.py", line 145, in visit_assignment func_node=func_node, ^^^^^^^^^ UnboundLocalError: cannot access local variable 'func_node' where it is not associated with a value ``` Signed-off-by: Eric Brown --- precli/parsers/python.py | 2 +- .../unit/parsers/examples/expression_list_assignment.py | 6 ++---- .../examples/expression_list_assignment_uneven.py | 6 ++++++ tests/unit/parsers/test_python.py | 9 +++++++++ 4 files changed, 18 insertions(+), 5 deletions(-) create mode 100644 tests/unit/parsers/examples/expression_list_assignment_uneven.py diff --git a/precli/parsers/python.py b/precli/parsers/python.py index c0f97744..c3a58f25 100644 --- a/precli/parsers/python.py +++ b/precli/parsers/python.py @@ -131,7 +131,7 @@ def visit_assignment(self, nodes: list[Node]): nodes[2].children[1] ) - if self.context["node"].children: + if nodes[2].children: # (attribute | identifier) argument_list func_node = nodes[2].children[0] var_node = self._get_var_node(func_node) diff --git a/tests/unit/parsers/examples/expression_list_assignment.py b/tests/unit/parsers/examples/expression_list_assignment.py index f75f22ed..1933a07b 100644 --- a/tests/unit/parsers/examples/expression_list_assignment.py +++ b/tests/unit/parsers/examples/expression_list_assignment.py @@ -1,6 +1,4 @@ -import torch +import ssl -torch.tensor([[0.1, 1.2], [2.2, 3.1], [4.9, 5.2]]) -x = torch.tensor([[0.1, 1.2], [2.2, 3.1], [4.9, 5.2]]) -b, *_, device = *x.shape, x.device +ssl_ctx1, ssl_ctx2 = ssl.SSLContext(), ssl.SSLContext() diff --git a/tests/unit/parsers/examples/expression_list_assignment_uneven.py b/tests/unit/parsers/examples/expression_list_assignment_uneven.py new file mode 100644 index 00000000..f75f22ed --- /dev/null +++ b/tests/unit/parsers/examples/expression_list_assignment_uneven.py @@ -0,0 +1,6 @@ +import torch + + +torch.tensor([[0.1, 1.2], [2.2, 3.1], [4.9, 5.2]]) +x = torch.tensor([[0.1, 1.2], [2.2, 3.1], [4.9, 5.2]]) +b, *_, device = *x.shape, x.device diff --git a/tests/unit/parsers/test_python.py b/tests/unit/parsers/test_python.py index 8003324c..9a89ea36 100644 --- a/tests/unit/parsers/test_python.py +++ b/tests/unit/parsers/test_python.py @@ -26,6 +26,15 @@ def test_expression_list_assignment(self): results = self.parser.parse(artifact) self.assertEqual(0, len(results)) + def test_expression_list_assignment_uneven(self): + artifact = Artifact( + os.path.join( + self.base_path, "expression_list_assignment_uneven.py" + ) + ) + results = self.parser.parse(artifact) + self.assertEqual(0, len(results)) + def test_importlib_import_module(self): artifact = Artifact( os.path.join(self.base_path, "importlib_import_module.py")