diff options
author | Jaehoon Hwang <jaehoonhwang@users.noreply.github.com> | 2021-10-09 23:18:46 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-10-10 08:18:46 +0200 |
commit | 220e27dc5bdd6bdd9dbee56d5c7d33a946c8ad17 (patch) | |
tree | c3f34d216acce183b92b7007f4a38811169d4c66 | |
parent | 661703f3c9f030420d6559433b621abdc27ac7b5 (diff) | |
download | pylint-git-220e27dc5bdd6bdd9dbee56d5c7d33a946c8ad17.tar.gz |
Rename `len-as-condition` to `use-implicit-booleaness-not-len` (#5132)
Rename `len-as-condition` to be more general for new checker
`use-implicit-booleaness-not-comparison`
* Refactor `LenChecker` class -> `ImplicitBooleanessChecker`o
* Rename test files/`len_checker.py`/`__init__.py` to reflect new name.
* Add `len-as-condition` as `old_names` for `use-implicit-booleaness-not-len`
Co-authored-by: Pierre Sassoulas <pierre.sassoulas@gmail.com>
-rw-r--r-- | CONTRIBUTORS.txt | 2 | ||||
-rw-r--r-- | ChangeLog | 4 | ||||
-rw-r--r-- | doc/whatsnew/2.12.rst | 4 | ||||
-rw-r--r-- | pylint/checkers/refactoring/__init__.py | 13 | ||||
-rw-r--r-- | pylint/checkers/refactoring/implicit_booleaness_checker.py (renamed from pylint/checkers/refactoring/len_checker.py) | 19 | ||||
-rw-r--r-- | tests/checkers/unittest_refactoring.py | 10 | ||||
-rw-r--r-- | tests/functional/l/len_checks.txt | 25 | ||||
-rw-r--r-- | tests/functional/u/use/use_implicit_booleaness_not_len.py (renamed from tests/functional/l/len_checks.py) | 54 | ||||
-rw-r--r-- | tests/functional/u/use/use_implicit_booleaness_not_len.txt | 25 |
9 files changed, 89 insertions, 67 deletions
diff --git a/CONTRIBUTORS.txt b/CONTRIBUTORS.txt index 9e44c497b..31c47ac77 100644 --- a/CONTRIBUTORS.txt +++ b/CONTRIBUTORS.txt @@ -549,4 +549,6 @@ contributors: * Tim Martin: contributor +* Jaehoon Hwang (jaehoonhwang): contributor + * Samuel Forestier: contributor @@ -18,6 +18,10 @@ Release date: TBA Closes #3859 +* In length checker, ``len-as-condition`` has been renamed as + ``use-implicit-booleaness-not-len`` in order to be consistent with + ``use-implicit-booleaness-not-comparison``. + What's New in Pylint 2.11.2? ============================ diff --git a/doc/whatsnew/2.12.rst b/doc/whatsnew/2.12.rst index 9bb00708e..494393adb 100644 --- a/doc/whatsnew/2.12.rst +++ b/doc/whatsnew/2.12.rst @@ -27,3 +27,7 @@ Other Changes * Improve and flatten ``unused-wildcard-import`` message Closes #3859 + +* In length checker, ``len-as-condition`` has been renamed as + ``use-implicit-booleaness-not-len`` in order to be consistent with + ``use-implicit-booleaness-not-comparison``. diff --git a/pylint/checkers/refactoring/__init__.py b/pylint/checkers/refactoring/__init__.py index 9208634ff..92cc1fd12 100644 --- a/pylint/checkers/refactoring/__init__.py +++ b/pylint/checkers/refactoring/__init__.py @@ -37,12 +37,19 @@ """Looks for code which can be refactored.""" -from pylint.checkers.refactoring.len_checker import LenChecker +from pylint.checkers.refactoring.implicit_booleaness_checker import ( + ImplicitBooleanessChecker, +) from pylint.checkers.refactoring.not_checker import NotChecker from pylint.checkers.refactoring.recommendation_checker import RecommendationChecker from pylint.checkers.refactoring.refactoring_checker import RefactoringChecker -__all__ = ["LenChecker", "NotChecker", "RecommendationChecker", "RefactoringChecker"] +__all__ = [ + "ImplicitBooleanessChecker", + "NotChecker", + "RecommendationChecker", + "RefactoringChecker", +] def register(linter): @@ -50,4 +57,4 @@ def register(linter): linter.register_checker(RefactoringChecker(linter)) linter.register_checker(NotChecker(linter)) linter.register_checker(RecommendationChecker(linter)) - linter.register_checker(LenChecker(linter)) + linter.register_checker(ImplicitBooleanessChecker(linter)) diff --git a/pylint/checkers/refactoring/len_checker.py b/pylint/checkers/refactoring/implicit_booleaness_checker.py index 4e4eb2b46..98605635c 100644 --- a/pylint/checkers/refactoring/len_checker.py +++ b/pylint/checkers/refactoring/implicit_booleaness_checker.py @@ -9,7 +9,7 @@ from pylint import checkers, interfaces from pylint.checkers import utils -class LenChecker(checkers.BaseChecker): +class ImplicitBooleanessChecker(checkers.BaseChecker): """Checks for incorrect usage of len() inside conditions. Pep8 states: For sequences, (strings, lists, tuples), use the fact that empty sequences are false. @@ -37,21 +37,22 @@ class LenChecker(checkers.BaseChecker): # configuration section name name = "refactoring" msgs = { - "C1801": ( + "C1802": ( "Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty", - "len-as-condition", + "use-implicit-booleaness-not-len", "Used when Pylint detects that len(sequence) is being used " "without explicit comparison inside a condition to determine if a sequence is empty. " "Instead of coercing the length to a boolean, either " "rely on the fact that empty sequences are false or " "compare the length against a scalar.", - ) + {"old_names": [("C1801", "len-as-condition")]}, + ), } priority = -2 options = () - @utils.check_messages("len-as-condition") + @utils.check_messages("use-implicit-booleaness-not-len") def visit_call(self, node: nodes.Call) -> None: # a len(S) call is used inside a test condition # could be if, while, assert or if expression statement @@ -76,7 +77,7 @@ class LenChecker(checkers.BaseChecker): ) if isinstance(len_arg, generator_or_comprehension): # The node is a generator or comprehension as in len([x for x in ...]) - self.add_message("len-as-condition", node=node) + self.add_message("use-implicit-booleaness-not-len", node=node) return try: instance = next(len_arg.infer()) @@ -90,7 +91,7 @@ class LenChecker(checkers.BaseChecker): if "range" in mother_classes or ( affected_by_pep8 and not self.instance_has_bool(instance) ): - self.add_message("len-as-condition", node=node) + self.add_message("use-implicit-booleaness-not-len", node=node) @staticmethod def instance_has_bool(class_def: nodes.ClassDef) -> bool: @@ -101,7 +102,7 @@ class LenChecker(checkers.BaseChecker): ... return False - @utils.check_messages("len-as-condition") + @utils.check_messages("use-implicit-booleaness-not-len") def visit_unaryop(self, node: nodes.UnaryOp) -> None: """`not len(S)` must become `not S` regardless if the parent block is a test condition or something else (boolean expression) @@ -111,7 +112,7 @@ class LenChecker(checkers.BaseChecker): and node.op == "not" and utils.is_call_of_name(node.operand, "len") ): - self.add_message("len-as-condition", node=node) + self.add_message("use-implicit-booleaness-not-len", node=node) @staticmethod def base_classes_of_node(instance: nodes.ClassDef) -> List[nodes.Name]: diff --git a/tests/checkers/unittest_refactoring.py b/tests/checkers/unittest_refactoring.py index 4b132e218..3c87a8d33 100644 --- a/tests/checkers/unittest_refactoring.py +++ b/tests/checkers/unittest_refactoring.py @@ -3,7 +3,7 @@ import astroid -from pylint.checkers.refactoring import LenChecker +from pylint.checkers.refactoring import ImplicitBooleanessChecker def test_class_tree_detection() -> None: @@ -24,23 +24,23 @@ class ChildClassWithoutBool(ClassWithoutBool): """ ) with_bool, without_bool, child_with_bool, child_without_bool = module.body - assert LenChecker().base_classes_of_node(with_bool) == [ + assert ImplicitBooleanessChecker().base_classes_of_node(with_bool) == [ "ClassWithBool", "list", "object", ] - assert LenChecker().base_classes_of_node(without_bool) == [ + assert ImplicitBooleanessChecker().base_classes_of_node(without_bool) == [ "ClassWithoutBool", "dict", "object", ] - assert LenChecker().base_classes_of_node(child_with_bool) == [ + assert ImplicitBooleanessChecker().base_classes_of_node(child_with_bool) == [ "ChildClassWithBool", "ClassWithBool", "list", "object", ] - assert LenChecker().base_classes_of_node(child_without_bool) == [ + assert ImplicitBooleanessChecker().base_classes_of_node(child_without_bool) == [ "ChildClassWithoutBool", "ClassWithoutBool", "dict", diff --git a/tests/functional/l/len_checks.txt b/tests/functional/l/len_checks.txt deleted file mode 100644 index f1b96e477..000000000 --- a/tests/functional/l/len_checks.txt +++ /dev/null @@ -1,25 +0,0 @@ -len-as-condition:4:3::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:7:3::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:11:9::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:14:11::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:55:5::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:60:5::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:63:6::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:66:6::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:69:12::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:72:6::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:95:11:github_issue_1331_v2:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:98:11:github_issue_1331_v3:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:101:17:github_issue_1331_v4:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:103:9::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:104:9::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:124:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:125:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:126:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:127:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:128:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:129:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:130:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -len-as-condition:171:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty -undefined-variable:183:11:github_issue_4215:Undefined variable 'undefined_var' -undefined-variable:185:11:github_issue_4215:Undefined variable 'undefined_var2' diff --git a/tests/functional/l/len_checks.py b/tests/functional/u/use/use_implicit_booleaness_not_len.py index ceeedb549..b4107ac2d 100644 --- a/tests/functional/l/len_checks.py +++ b/tests/functional/u/use/use_implicit_booleaness_not_len.py @@ -1,17 +1,17 @@ # pylint: disable=too-few-public-methods,import-error, missing-docstring, misplaced-comparison-constant # pylint: disable=useless-super-delegation,wrong-import-position,invalid-name, wrong-import-order, condition-evals-to-constant -if len('TEST'): # [len-as-condition] +if len('TEST'): # [use-implicit-booleaness-not-len] pass -if not len('TEST'): # [len-as-condition] +if not len('TEST'): # [use-implicit-booleaness-not-len] pass z = [] -if z and len(['T', 'E', 'S', 'T']): # [len-as-condition] +if z and len(['T', 'E', 'S', 'T']): # [use-implicit-booleaness-not-len] pass -if True or len('TEST'): # [len-as-condition] +if True or len('TEST'): # [use-implicit-booleaness-not-len] pass if len('TEST') == 0: # Should be fine @@ -52,24 +52,24 @@ if z or 10 > len('TEST') != 0: # Should be fine if z: pass -elif len('TEST'): # [len-as-condition] +elif len('TEST'): # [use-implicit-booleaness-not-len] pass if z: pass -elif not len('TEST'): # [len-as-condition] +elif not len('TEST'): # [use-implicit-booleaness-not-len] pass -while len('TEST'): # [len-as-condition] +while len('TEST'): # [use-implicit-booleaness-not-len] pass -while not len('TEST'): # [len-as-condition] +while not len('TEST'): # [use-implicit-booleaness-not-len] pass -while z and len('TEST'): # [len-as-condition] +while z and len('TEST'): # [use-implicit-booleaness-not-len] pass -while not len('TEST') and z: # [len-as-condition] +while not len('TEST') and z: # [use-implicit-booleaness-not-len] pass assert len('TEST') > 0 # Should be fine @@ -92,17 +92,16 @@ def github_issue_1331(*args): assert False, len(args) # Should be fine def github_issue_1331_v2(*args): - assert len(args), args # [len-as-condition] + assert len(args), args # [use-implicit-booleaness-not-len] def github_issue_1331_v3(*args): - assert len(args) or z, args # [len-as-condition] + assert len(args) or z, args # [use-implicit-booleaness-not-len] def github_issue_1331_v4(*args): - assert z and len(args), args # [len-as-condition] - -b = bool(len(z)) # [len-as-condition] -c = bool(len('TEST') or 42) # [len-as-condition] + assert z and len(args), args # [use-implicit-booleaness-not-len] +b = bool(len(z)) # [use-implicit-booleaness-not-len] +c = bool(len('TEST') or 42) # [use-implicit-booleaness-not-len] def github_issue_1879(): @@ -121,13 +120,13 @@ def github_issue_1879(): assert len(ClassWithBool()) assert len(ChildClassWithBool()) - assert len(ClassWithoutBool()) # [len-as-condition] - assert len(ChildClassWithoutBool()) # [len-as-condition] - assert len(range(0)) # [len-as-condition] - assert len([t + 1 for t in []]) # [len-as-condition] - assert len(u + 1 for u in []) # [len-as-condition] - assert len({"1":(v + 1) for v in {}}) # [len-as-condition] - assert len(set((w + 1) for w in set())) # [len-as-condition] + assert len(ClassWithoutBool()) # [use-implicit-booleaness-not-len] + assert len(ChildClassWithoutBool()) # [use-implicit-booleaness-not-len] + assert len(range(0)) # [use-implicit-booleaness-not-len] + assert len([t + 1 for t in []]) # [use-implicit-booleaness-not-len] + assert len(u + 1 for u in []) # [use-implicit-booleaness-not-len] + assert len({"1":(v + 1) for v in {}}) # [use-implicit-booleaness-not-len] + assert len(set((w + 1) for w in set())) # [use-implicit-booleaness-not-len] # pylint: disable=import-outside-toplevel import numpy @@ -168,9 +167,9 @@ def github_issue_1879(): # def function_returning_function(r): # return function_returning_generator(r) - assert len(function_returning_list(z)) # [len-as-condition] + assert len(function_returning_list(z)) # [use-implicit-booleaness-not-len] assert len(function_returning_int(z)) - # This should raise a len-as-conditions once astroid can infer it + # This should raise a use-implicit-booleaness-not-len once astroid can infer it # See https://github.com/PyCQA/pylint/pull/3821#issuecomment-743771514 # assert len(function_returning_generator(z)) # assert len(function_returning_comprehension(z)) @@ -184,3 +183,8 @@ def github_issue_4215(): pass if len(undefined_var2[0]): # [undefined-variable] pass + +# pylint: disable=len-as-condition + +if len('TEST'): + pass diff --git a/tests/functional/u/use/use_implicit_booleaness_not_len.txt b/tests/functional/u/use/use_implicit_booleaness_not_len.txt new file mode 100644 index 000000000..f5020c80e --- /dev/null +++ b/tests/functional/u/use/use_implicit_booleaness_not_len.txt @@ -0,0 +1,25 @@ +use-implicit-booleaness-not-len:4:3::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:7:3::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:11:9::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:14:11::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:55:5::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:60:5::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:63:6::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:66:6::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:69:12::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:72:6::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:95:11:github_issue_1331_v2:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:98:11:github_issue_1331_v3:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:101:17:github_issue_1331_v4:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:103:9::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:104:9::Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:123:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:124:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:125:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:126:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:127:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:128:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:129:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +use-implicit-booleaness-not-len:170:11:github_issue_1879:Do not use `len(SEQUENCE)` without comparison to determine if a sequence is empty:HIGH +undefined-variable:182:11:github_issue_4215:Undefined variable 'undefined_var':HIGH +undefined-variable:184:11:github_issue_4215:Undefined variable 'undefined_var2':HIGH |