PyCQA / flake8-bugbear

A plugin for Flake8 finding likely bugs and design problems in your program. Contains warnings that don't belong in pyflakes and pycodestyle.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

B017: False negative when "from" imports used

Klim314 opened this issue · comments

Summary

B017 fails when raises is imported directly

Version

Replicated on version 23.9.16

Sample code

import pytest
from pytest import raises


def foo():
    raise


def test_pytest_raises():
    with raises(Exception):
        foo()
    with pytest.raises(Exception):
        foo()

Nice find. Will happily take a fix to include supporting this.

I'm interested in doing a PR for this fix, however I have a question about how best to go about avoiding false positives.

The most obvious solution modifies the check for B017 to also be "positive" for an ast.Name object with id == "raises", but this would also falsely flag from Dummy import raises.

After looking further into the code, the most straightforward solution, to me, seems to me

  1. Add visit_ImportFrom(self, node) that then calls visitImport(...) to perform the same checks.
    • As-is, the ast.ImportFrom node is not handled in any way
    • I have verified that the B005 check method is entered with both types of import nodes after this change
  2. Modify the logic of check_for_b005 to account for the possibility of an ast.ImportFrom node
    • It seems like the solution would be to add an "or" to the first condition, if isinstance(node, ast.Import) or isinstance(node, ast.ImportFrom) so that the node would be added to self._b005_imports
    • Is there anything else that would need to be changed to support ast.ImportFrom node? If so, would that be expected to be don as part of this PR, or create a new issue to log the needed change?
  3. Modify the logic in check_for_b017 to check for: ast.Name node with id = "raises" and an ast.ImportFrom node in _b005_imports that indicates the from pytest import raises node
  • This check should account for the possibility that the node is from pytest import ..., raises, ... (multiple imports in one line)
  • Would only the check for raises() have an matches argument be the only check that should be added (if possible)?

I want to make sure this approach is a reasonable solution before I get too far into the development, particularly the changes to check_for_b005 and how to handle the ast.ImportFrom node. Do you think this makes sense for a solution?