""" Checks that reversed() receive proper argument """ # pylint: disable=missing-docstring # pylint: disable=too-few-public-methods from collections import deque, OrderedDict from enum import IntEnum class GoodReversed: """ Implements __reversed__ """ def __reversed__(self): return [1, 2, 3] class SecondGoodReversed: """ Implements __len__ and __getitem__ """ def __len__(self): return 3 def __getitem__(self, index): return index class BadReversed: """ implements only len() """ def __len__(self): return 3 class SecondBadReversed: """ implements only __getitem__ """ def __getitem__(self, index): return index def uninferable(seq): """ This can't be inferred at this moment, make sure we don't have a false positive. """ return reversed(seq) def test(path): """ test function """ seq = reversed() # No argument given seq = reversed(None) # [bad-reversed-sequence] seq = reversed([1, 2, 3]) seq = reversed((1, 2, 3)) seq = reversed(set()) # [bad-reversed-sequence] seq = reversed(iter([1, 2, 3])) # [bad-reversed-sequence] seq = reversed(GoodReversed()) seq = reversed(SecondGoodReversed()) seq = reversed(BadReversed()) # [bad-reversed-sequence] seq = reversed(SecondBadReversed()) # [bad-reversed-sequence] seq = reversed(range(100)) seq = reversed(lambda: None) # [bad-reversed-sequence] seq = reversed(deque([])) seq = reversed("123") seq = uninferable([1, 2, 3]) seq = reversed(path.split("/")) return seq def test_dict_ancestor_and_reversed(): """Don't emit for subclasses of dict, with __reversed__ implemented.""" class Child(dict): def __reversed__(self): return reversed(range(10)) seq = reversed(OrderedDict()) return reversed(Child()), seq def test_dont_emit_for_reversing_enums(): """Don't emit when reversing enum classes""" class Color(IntEnum): RED = 1 GREEN = 2 BLUE = 3 for color in reversed(Color): yield color