mirror of
https://github.com/astral-sh/ruff.git
synced 2025-07-22 20:45:11 +00:00
[refurb
] Implement single-item-membership-test
(FURB171
) (#7815)
## Summary Implement [`no-single-item-in`](https://github.com/dosisod/refurb/blob/master/refurb/checks/iterable/no_single_item_in.py) as `single-item-membership-test` (`FURB171`). Uses the helper function `generate_comparison` from the `pycodestyle` implementations; this function should probably be moved, but I am not sure where at the moment. Update: moved it to `ruff_python_ast::helpers`. Related to #1348. ## Test Plan `cargo test`
This commit is contained in:
parent
bdd925c0f2
commit
62f1ee08e7
12 changed files with 368 additions and 63 deletions
|
@ -1,14 +1,19 @@
|
|||
use std::borrow::Cow;
|
||||
use std::path::Path;
|
||||
|
||||
use ruff_python_trivia::CommentRanges;
|
||||
use ruff_source_file::Locator;
|
||||
use smallvec::SmallVec;
|
||||
|
||||
use ruff_text_size::{Ranged, TextRange};
|
||||
|
||||
use crate::call_path::CallPath;
|
||||
use crate::node::AnyNodeRef;
|
||||
use crate::parenthesize::parenthesized_range;
|
||||
use crate::statement_visitor::{walk_body, walk_stmt, StatementVisitor};
|
||||
use crate::{
|
||||
self as ast, Arguments, Constant, ExceptHandler, Expr, MatchCase, Pattern, Stmt, TypeParam,
|
||||
self as ast, Arguments, CmpOp, Constant, ExceptHandler, Expr, MatchCase, Pattern, Stmt,
|
||||
TypeParam,
|
||||
};
|
||||
|
||||
/// Return `true` if the `Stmt` is a compound statement (as opposed to a simple statement).
|
||||
|
@ -1129,6 +1134,58 @@ impl Truthiness {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn generate_comparison(
|
||||
left: &Expr,
|
||||
ops: &[CmpOp],
|
||||
comparators: &[Expr],
|
||||
parent: AnyNodeRef,
|
||||
comment_ranges: &CommentRanges,
|
||||
locator: &Locator,
|
||||
) -> String {
|
||||
let start = left.start();
|
||||
let end = comparators.last().map_or_else(|| left.end(), Ranged::end);
|
||||
let mut contents = String::with_capacity(usize::from(end - start));
|
||||
|
||||
// Add the left side of the comparison.
|
||||
contents.push_str(
|
||||
locator.slice(
|
||||
parenthesized_range(left.into(), parent, comment_ranges, locator.contents())
|
||||
.unwrap_or(left.range()),
|
||||
),
|
||||
);
|
||||
|
||||
for (op, comparator) in ops.iter().zip(comparators) {
|
||||
// Add the operator.
|
||||
contents.push_str(match op {
|
||||
CmpOp::Eq => " == ",
|
||||
CmpOp::NotEq => " != ",
|
||||
CmpOp::Lt => " < ",
|
||||
CmpOp::LtE => " <= ",
|
||||
CmpOp::Gt => " > ",
|
||||
CmpOp::GtE => " >= ",
|
||||
CmpOp::In => " in ",
|
||||
CmpOp::NotIn => " not in ",
|
||||
CmpOp::Is => " is ",
|
||||
CmpOp::IsNot => " is not ",
|
||||
});
|
||||
|
||||
// Add the right side of the comparison.
|
||||
contents.push_str(
|
||||
locator.slice(
|
||||
parenthesized_range(
|
||||
comparator.into(),
|
||||
parent,
|
||||
comment_ranges,
|
||||
locator.contents(),
|
||||
)
|
||||
.unwrap_or(comparator.range()),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
contents
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use std::borrow::Cow;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue