diff --git a/crates/ruff_linter/resources/test/fixtures/pep8_naming/N817.py b/crates/ruff_linter/resources/test/fixtures/pep8_naming/N817.py index 277fcc4789e84..b6862515b7c46 100644 --- a/crates/ruff_linter/resources/test/fixtures/pep8_naming/N817.py +++ b/crates/ruff_linter/resources/test/fixtures/pep8_naming/N817.py @@ -4,3 +4,7 @@ # OK depending on configured import convention import xml.etree.ElementTree as ET +from xml.etree import ElementTree as ET + +# Always an error (relative import) +from ..xml.eltree import ElementTree as ET diff --git a/crates/ruff_linter/src/rules/pep8_naming/rules/camelcase_imported_as_acronym.rs b/crates/ruff_linter/src/rules/pep8_naming/rules/camelcase_imported_as_acronym.rs index 65aeaaec22503..0ce8db355371b 100644 --- a/crates/ruff_linter/src/rules/pep8_naming/rules/camelcase_imported_as_acronym.rs +++ b/crates/ruff_linter/src/rules/pep8_naming/rules/camelcase_imported_as_acronym.rs @@ -74,14 +74,7 @@ pub(crate) fn camelcase_imported_as_acronym( } // Ignore names that follow a community-agreed import convention. - if checker - .settings - .flake8_import_conventions - .aliases - .get(&*alias.name) - .map(String::as_str) - == Some(asname) - { + if is_ignored_because_of_import_convention(asname, stmt, alias, checker) { return None; } @@ -97,3 +90,34 @@ pub(crate) fn camelcase_imported_as_acronym( } None } + +fn is_ignored_because_of_import_convention( + asname: &str, + stmt: &Stmt, + alias: &Alias, + checker: &Checker, +) -> bool { + let full_name = if let Some(import_from) = stmt.as_import_from_stmt() { + // Never test relative imports for exclusion because we can't resolve the full-module name. + let Some(module) = import_from.module.as_ref() else { + return false; + }; + + if import_from.level != 0 { + return false; + } + + std::borrow::Cow::Owned(format!("{module}.{}", alias.name)) + } else { + std::borrow::Cow::Borrowed(&*alias.name) + }; + + // Ignore names that follow a community-agreed import convention. + checker + .settings + .flake8_import_conventions + .aliases + .get(&*full_name) + .map(String::as_str) + == Some(asname) +} diff --git a/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__N817_N817.py.snap b/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__N817_N817.py.snap index 5615c1fca35c9..63fa4b0f165ac 100644 --- a/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__N817_N817.py.snap +++ b/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__N817_N817.py.snap @@ -15,4 +15,9 @@ N817.py:2:17: N817 CamelCase `CamelCase` imported as acronym `CC` | ^^^^^^^^^^^^^^^ N817 | - +N817.py:10:26: N817 CamelCase `ElementTree` imported as acronym `ET` + | + 9 | # Always an error (relative import) +10 | from ..xml.eltree import ElementTree as ET + | ^^^^^^^^^^^^^^^^^ N817 + | diff --git a/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__camelcase_imported_as_incorrect_convention.snap b/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__camelcase_imported_as_incorrect_convention.snap index f0e6867ab3255..9eb17d9ae9c51 100644 --- a/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__camelcase_imported_as_incorrect_convention.snap +++ b/crates/ruff_linter/src/rules/pep8_naming/snapshots/ruff_linter__rules__pep8_naming__tests__camelcase_imported_as_incorrect_convention.snap @@ -20,4 +20,22 @@ N817.py:6:8: N817 CamelCase `ElementTree` imported as acronym `ET` 5 | # OK depending on configured import convention 6 | import xml.etree.ElementTree as ET | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ N817 +7 | from xml.etree import ElementTree as ET | + +N817.py:7:23: N817 CamelCase `ElementTree` imported as acronym `ET` + | +5 | # OK depending on configured import convention +6 | import xml.etree.ElementTree as ET +7 | from xml.etree import ElementTree as ET + | ^^^^^^^^^^^^^^^^^ N817 +8 | +9 | # Always an error (relative import) + | + +N817.py:10:26: N817 CamelCase `ElementTree` imported as acronym `ET` + | + 9 | # Always an error (relative import) +10 | from ..xml.eltree import ElementTree as ET + | ^^^^^^^^^^^^^^^^^ N817 + |