Repository: MartinThoma/flake8-simplify (python)

Issue:
[Adjust Rule] SIM110
## Desired change

* **Rule(s)**: SIM110
* **Adjustment**: Fix issue

## Example

This is an example where the mentioned rule(s) would currently be suboptimal:

```python
#  Code
for el in [1,2,3]:
    if is_true(el):
        return True
raise Exception

# Current message
SIM110 Use 'return any(is_true(el) for el in [1, 2, 3])'

# Desired message: Either none or the following:
SIM110 Use 'if any(is_true(el) for el in [1, 2, 3]): return True; raise Exception'
```


Pull request:
SIM110: Remove false-positives
BUG: Don't show SIM110 when an exception is returned instead of
returning

Closes #34

Patch:
diff --git a/flake8_simplify.py b/flake8_simplify.py
index a49f270..f4292b1 100644
--- a/flake8_simplify.py
+++ b/flake8_simplify.py
@@ -612,6 +612,8 @@ def _get_sim110_sim111(node: ast.For) -> List[Tuple[int, int, str]]:
         return errors
     if not hasattr(node.body[0].body[0].value, "value"):
         return errors
+    if isinstance(node.next_sibling, ast.Raise):  # type: ignore
+        return errors
     check = to_source(node.body[0].test)
     target = to_source(node.target)
     iterable = to_source(node.iter)
@@ -1202,7 +1204,15 @@ def is_stmt_equal(a: ast.stmt, b: ast.stmt) -> bool:
     if type(a) is not type(b):
         return False
     if isinstance(a, ast.AST):
-        specials = ("lineno", "col_offset", "ctx", "end_lineno", "parent")
+        specials = (
+            "lineno",
+            "col_offset",
+            "ctx",
+            "end_lineno",
+            "parent",
+            "previous_sibling",
+            "next_sibling",
+        )
         for k, v in vars(a).items():
             if k.startswith("_") or k in specials:
                 continue
@@ -1916,8 +1926,13 @@ class Plugin:
 
         # Add parent
         for node in ast.walk(self._tree):
+            previous_sibling = None
             for child in ast.iter_child_nodes(node):
+                child.previous_sibling = previous_sibling  # type: ignore
+                if previous_sibling:
+                    child.previous_sibling.next_sibling = child  # type: ignore
                 child.parent = node  # type: ignore
+                previous_sibling = child
         visitor.visit(self._tree)
 
         for line, col, msg in visitor.errors:


Test patch:
diff --git a/tests/test_simplify.py b/tests/test_simplify.py
index 9efd092..5443746 100644
--- a/tests/test_simplify.py
+++ b/tests/test_simplify.py
@@ -291,7 +291,6 @@ return False"""
     assert ret == {"1:0 SIM110 Use 'return any(check(x) for x in iterable)'"}
 
 
-@pytest.mark.xfail(reason="See issue #34: False-positive for SIM110")
 def test_sim110_raise_exception():
     ret = _results(
         """
@@ -300,7 +299,8 @@ for el in [1,2,3]:
         return True
 raise Exception"""
     )
-    assert ret == set()
+    for el in ret:
+        assert "SIM110" not in el
 
 
 def test_sim111_all():