Files
ruff/src/rules/flake8_debugger/rules.rs
Charlie Marsh dae95626ae Use smallvec for call path representation (#1960)
This provides a ~10% speed-up for large codebases with `--select ALL`:

![Screen Shot 2023-01-18 at 11 28 20 AM](https://user-images.githubusercontent.com/1309177/213236389-cff50840-6e55-47a3-9164-2e40cbc885f6.png)
2023-01-18 11:29:05 -05:00

73 lines
2.3 KiB
Rust

use rustpython_ast::{Expr, Stmt};
use super::types::DebuggerUsingType;
use crate::ast::helpers::format_call_path;
use crate::ast::types::Range;
use crate::checkers::ast::Checker;
use crate::registry::Diagnostic;
use crate::violations;
const DEBUGGERS: &[&[&str]] = &[
&["pdb", "set_trace"],
&["pudb", "set_trace"],
&["ipdb", "set_trace"],
&["ipdb", "sset_trace"],
&["IPython", "terminal", "embed", "InteractiveShellEmbed"],
&[
"IPython",
"frontend",
"terminal",
"embed",
"InteractiveShellEmbed",
],
&["celery", "contrib", "rdb", "set_trace"],
&["builtins", "breakpoint"],
&["", "breakpoint"],
];
/// Checks for the presence of a debugger call.
pub fn debugger_call(checker: &mut Checker, expr: &Expr, func: &Expr) {
if let Some(target) = checker.resolve_call_path(func).and_then(|call_path| {
DEBUGGERS
.iter()
.find(|target| call_path.as_slice() == **target)
}) {
checker.diagnostics.push(Diagnostic::new(
violations::Debugger(DebuggerUsingType::Call(format_call_path(target))),
Range::from_located(expr),
));
}
}
/// Checks for the presence of a debugger import.
pub fn debugger_import(stmt: &Stmt, module: Option<&str>, name: &str) -> Option<Diagnostic> {
// Special-case: allow `import builtins`, which is far more general than (e.g.)
// `import celery.contrib.rdb`).
if module.is_none() && name == "builtins" {
return None;
}
if let Some(module) = module {
let mut call_path = module.split('.').collect::<Vec<_>>();
call_path.push(name);
if DEBUGGERS.iter().any(|target| call_path == **target) {
return Some(Diagnostic::new(
violations::Debugger(DebuggerUsingType::Import(format_call_path(&call_path))),
Range::from_located(stmt),
));
}
} else {
let parts = name.split('.').collect::<Vec<_>>();
if DEBUGGERS
.iter()
.any(|call_path| call_path[..call_path.len() - 1] == parts)
{
return Some(Diagnostic::new(
violations::Debugger(DebuggerUsingType::Import(name.to_string())),
Range::from_located(stmt),
));
}
}
None
}