diff options
author | Sylvain Th?nault <sylvain.thenault@logilab.fr> | 2013-12-20 14:02:56 +0100 |
---|---|---|
committer | Sylvain Th?nault <sylvain.thenault@logilab.fr> | 2013-12-20 14:02:56 +0100 |
commit | 7ecac59ebc534e869a772efa6dbd973fb8843f44 (patch) | |
tree | 2daee1dec8ece74c20efcdb3acae14043b0d13f3 | |
parent | 9f6eb6490cdc13ce1a99ad68ec66e7fa93b07c95 (diff) | |
download | pylint-7ecac59ebc534e869a772efa6dbd973fb8843f44.tar.gz |
fix unpacking-non-sequence false negative: detect that infered node **is an instance**
of an iterable class.
Also, slightly enhance the message for it and its unbalanced-tuple-unpackaging
cousin.
-rw-r--r-- | checkers/variables.py | 56 | ||||
-rw-r--r-- | test/messages/func_unbalanced_tuple_unpacking.txt | 11 | ||||
-rw-r--r-- | test/messages/func_unpacking_non_sequence.txt | 15 |
3 files changed, 43 insertions, 39 deletions
diff --git a/checkers/variables.py b/checkers/variables.py index 7f4ff1b..90b7fe7 100644 --- a/checkers/variables.py +++ b/checkers/variables.py @@ -51,6 +51,20 @@ def overridden_method(klass, name): return meth_node return None +def _get_unpacking_extra_info(node, infered): + """return extra information to add to the message for unpacking-non-sequence + and unbalanced-tuple-unpacking errors + """ + more = '' + infered_module = infered.root().name + if node.root().name == infered_module: + if node.lineno == infered.lineno: + more = ' %s' % infered.as_string() + elif infered.lineno: + more = ' defined at line %s' % infered.lineno + elif infered.lineno: + more = ' defined at line %s of %s' % (infered.lineno, infered_module) + return more MSGS = { 'E0601': ('Using variable %r before assignment', @@ -120,13 +134,12 @@ MSGS = { the loop.'), 'W0632': ('Possible unbalanced tuple unpacking with ' - 'sequence at line %s: ' + 'sequence%s: ' 'left side has %d label(s), right side has %d value(s)', 'unbalanced-tuple-unpacking', 'Used when there is an unbalanced tuple unpacking in assignment'), - 'W0633': ('Attempting to unpack a non-sequence with ' - 'non-sequence at line %s', + 'W0633': ('Attempting to unpack a non-sequence%s', 'unpacking-non-sequence', 'Used when something which is not ' 'a sequence is used in an unpack assignment'), @@ -572,41 +585,30 @@ builtins. Remember that you should avoid to define new builtins when possible.' """ Check for unbalanced tuple unpacking and unpacking non sequences. """ + if infered is astroid.YES: + return if isinstance(infered, (astroid.Tuple, astroid.List)): + # attempt to check unpacking is properly balanced values = infered.itered() if len(targets) != len(values): - if node.root().name == infered.root().name: - location = infered.lineno or 'unknown' - else: - location = '%s (%s)' % (infered.lineno or 'unknown', - infered.root().name) - - self.add_message('unbalanced-tuple-unpacking', - node=node, - args=(location, + self.add_message('unbalanced-tuple-unpacking', node=node, + args=(_get_unpacking_extra_info(node, infered), len(targets), len(values))) - else: - if infered is astroid.YES: - return - + # attempt to check unpacking may be possible (ie RHS is iterable) + elif isinstance(infered, astroid.Instance): for meth in ('__iter__', '__getitem__'): try: infered.getattr(meth) + break except astroid.NotFoundError: continue - else: - break else: - if node.root().name == infered.root().name: - location = infered.lineno or 'unknown' - else: - location = '%s (%s)' % (infered.lineno or 'unknown', - infered.root().name) - - self.add_message('unpacking-non-sequence', - node=node, - args=(location, )) + self.add_message('unpacking-non-sequence', node=node, + args=(_get_unpacking_extra_info(node, infered),)) + else: + self.add_message('unpacking-non-sequence', node=node, + args=(_get_unpacking_extra_info(node, infered),)) def _check_module_attrs(self, node, module, module_names): diff --git a/test/messages/func_unbalanced_tuple_unpacking.txt b/test/messages/func_unbalanced_tuple_unpacking.txt index 91880e7..c9311cc 100644 --- a/test/messages/func_unbalanced_tuple_unpacking.txt +++ b/test/messages/func_unbalanced_tuple_unpacking.txt @@ -1,5 +1,6 @@ -W: 9:do_stuff: Possible unbalanced tuple unpacking with sequence at line 9: left side has 2 label(s), right side has 3 value(s) -W: 14:do_stuff1: Possible unbalanced tuple unpacking with sequence at line 14: left side has 2 label(s), right side has 3 value(s) -W: 19:do_stuff2: Possible unbalanced tuple unpacking with sequence at line 19: left side has 2 label(s), right side has 3 value(s) -W: 50:do_stuff7: Possible unbalanced tuple unpacking with sequence at line 46: left side has 2 label(s), right side has 3 value(s) -W: 69:do_stuff9: Possible unbalanced tuple unpacking with sequence at line 7 (input.unpacking): left side has 2 label(s), right side has 3 value(s)
\ No newline at end of file +W: 9:do_stuff: Possible unbalanced tuple unpacking with sequence (1, 2, 3): left side has 2 label(s), right side has 3 value(s) +W: 14:do_stuff1: Possible unbalanced tuple unpacking with sequence [1, 2, 3]: left side has 2 label(s), right side has 3 value(s) +W: 19:do_stuff2: Possible unbalanced tuple unpacking with sequence (1, 2, 3): left side has 2 label(s), right side has 3 value(s) +W: 50:do_stuff7: Possible unbalanced tuple unpacking with sequence defined at line 46: left side has 2 label(s), right side has 3 value(s) +W: 69:do_stuff9: Possible unbalanced tuple unpacking with sequence defined at line 7 of input.unpacking: left side has 2 label(s), right side has 3 value(s) + diff --git a/test/messages/func_unpacking_non_sequence.txt b/test/messages/func_unpacking_non_sequence.txt index 087eb0e..55a7745 100644 --- a/test/messages/func_unpacking_non_sequence.txt +++ b/test/messages/func_unpacking_non_sequence.txt @@ -1,7 +1,8 @@ -W: 61: Attempting to unpack a non-sequence with non-sequence at line 52 -W: 63: Attempting to unpack a non-sequence with non-sequence at line 63 -W: 64: Attempting to unpack a non-sequence with non-sequence at line 64 -W: 65: Attempting to unpack a non-sequence with non-sequence at line 9 (input.unpacking) -W: 66: Attempting to unpack a non-sequence with non-sequence at line 11 (input.unpacking) -W: 67: Attempting to unpack a non-sequence with non-sequence at line 58 -W: 68: Attempting to unpack a non-sequence with non-sequence at line unknown (sys) +W: 61: Attempting to unpack a non-sequence defined at line 52 +W: 62: Attempting to unpack a non-sequence +W: 63: Attempting to unpack a non-sequence None +W: 64: Attempting to unpack a non-sequence 1 +W: 65: Attempting to unpack a non-sequence defined at line 9 of input.unpacking +W: 66: Attempting to unpack a non-sequence defined at line 11 of input.unpacking +W: 67: Attempting to unpack a non-sequence defined at line 58 +W: 68: Attempting to unpack a non-sequence |