[flake8-tidy-imports] extend autofix of relative imports (#2990)

This extends the autofix for TID252 to work with for relative imports without `module` (i.e. `from .. import`). Tested with `matplotlib` and `bokeh`.
(Previously it would panic on unwrap of the module) 

Note that pandas has [replaced](6057d7a93e) `absolufy-imports` with `ruff` now!
This commit is contained in:
Simon Brugman
2023-02-17 20:35:28 +01:00
committed by GitHub
parent 0dd590f137
commit a934d01bdb
3 changed files with 58 additions and 21 deletions

View File

@@ -4,4 +4,5 @@ import attrs
from ..protocol import commands, definitions, responses
from ..server import example
from .. import server
from . import logger, models

View File

@@ -92,34 +92,51 @@ fn fix_banned_relative_import(
module_path: Option<&Vec<String>>,
stylist: &Stylist,
) -> Option<Fix> {
// Only fix is the module path is known
// Only fix is the module path is known.
if let Some(mut parts) = module_path.cloned() {
// Remove relative level from module path
// Remove relative level from module path.
for _ in 0..*level? {
parts.pop();
}
let call_path = from_relative_import(&parts, module.unwrap());
let module_name = call_path.as_slice();
// Require import to be a valid PEP 8 module:
// https://python.org/dev/peps/pep-0008/#package-and-module-names
if module_name.iter().any(|f| !is_lower_with_underscore(f)) {
return None;
}
let content = match &stmt.node {
StmtKind::ImportFrom { names, .. } => unparse_stmt(
&create_stmt(StmtKind::ImportFrom {
module: Some(module_name.join(".")),
names: names.clone(),
level: Some(0),
}),
stylist,
),
_ => return None,
let module_name = if let Some(module) = module {
let call_path = from_relative_import(&parts, module);
// Require import to be a valid PEP 8 module:
// https://python.org/dev/peps/pep-0008/#package-and-module-names
if !call_path.iter().all(|part| is_lower_with_underscore(part)) {
return None;
}
call_path.as_slice().join(".")
} else if parts.len() > 1 {
let module = parts.last().unwrap();
let call_path = from_relative_import(&parts, module);
// Require import to be a valid PEP 8 module:
// https://python.org/dev/peps/pep-0008/#package-and-module-names
if !call_path.iter().all(|part| is_lower_with_underscore(part)) {
return None;
}
call_path.as_slice().join(".")
} else {
// Require import to be a valid PEP 8 module:
// https://python.org/dev/peps/pep-0008/#package-and-module-names
if !parts.iter().all(|part| is_lower_with_underscore(part)) {
return None;
}
parts.join(".")
};
let StmtKind::ImportFrom { names, .. } = &stmt.node else {
unreachable!("Expected StmtKind::ImportFrom");
};
let content = unparse_stmt(
&create_stmt(StmtKind::ImportFrom {
module: Some(module_name),
names: names.clone(),
level: Some(0),
}),
stylist,
);
Some(Fix::replacement(
content,
stmt.location,

View File

@@ -78,4 +78,23 @@ expression: diagnostics
row: 6
column: 28
parent: ~
- kind:
RelativeImports:
strictness: parents
location:
row: 7
column: 0
end_location:
row: 7
column: 21
fix:
content:
- from my_package.sublib.sublib import server
location:
row: 7
column: 0
end_location:
row: 7
column: 21
parent: ~