diff --git a/ChangeLog b/ChangeLog index 5189034a26..76beb4ba80 100644 --- a/ChangeLog +++ b/ChangeLog @@ -22,6 +22,14 @@ Release date: TBA Close #3141 +* Fix ``utils.is_error`` to account for functions returning early. + + This fixes a false negative with ``unused-variable`` which was no longer triggered + when a function raised an exception as the last instruction, but the body of the function + still had unused variables. + + Close #3028 + What's New in Pylint 2.4.1? =========================== diff --git a/pylint/checkers/utils.py b/pylint/checkers/utils.py index def655769d..22c44836a3 100644 --- a/pylint/checkers/utils.py +++ b/pylint/checkers/utils.py @@ -266,10 +266,14 @@ def is_super(node: astroid.node_classes.NodeNG) -> bool: def is_error(node: astroid.node_classes.NodeNG) -> bool: """return true if the function does nothing but raising an exception""" - for child_node in node.get_children(): + raises = False + returns = False + for child_node in node.nodes_of_class((astroid.Raise, astroid.Return)): if isinstance(child_node, astroid.Raise): - return True - return False + raises = True + if isinstance(child_node, astroid.Return): + returns = True + return raises and not returns builtins = builtins.__dict__.copy() # type: ignore diff --git a/tests/functional/u/unused_variable.py b/tests/functional/u/unused_variable.py index cb5215d99e..2d2c540b9e 100644 --- a/tests/functional/u/unused_variable.py +++ b/tests/functional/u/unused_variable.py @@ -58,3 +58,10 @@ def unused_import_from(): def unused_import_in_function(value): from six import PY2, text_type # [unused-import] return value.encode("utf-8") if PY2 else value + + +def hello(arg): + my_var = 'something' # [unused-variable] + if arg: + return True + raise Exception diff --git a/tests/functional/u/unused_variable.txt b/tests/functional/u/unused_variable.txt index e9f7ef0220..635324529c 100644 --- a/tests/functional/u/unused_variable.txt +++ b/tests/functional/u/unused_variable.txt @@ -11,3 +11,4 @@ unused-variable:46:locals_does_not_account_for_subscopes:Unused variable 'value' unused-import:54:unused_import_from:Unused wraps imported from functools as abc unused-import:55:unused_import_from:Unused namedtuple imported from collections unused-import:59:unused_import_in_function:Unused text_type imported from six +unused-variable:64:hello:Unused variable 'my_var'