Fix redundant closure with macros

This commit is contained in:
Cameron Steffen 2021-03-08 12:59:58 -06:00
parent d02ca3b81b
commit bf98aa6fb8
4 changed files with 72 additions and 14 deletions

View file

@ -10,6 +10,8 @@ use crate::utils::{
implements_trait, is_adjusted, iter_input_pats, snippet_opt, span_lint_and_sugg, span_lint_and_then,
type_is_unsafe_function,
};
use clippy_utils::higher;
use clippy_utils::higher::VecArgs;
declare_clippy_lint! {
/// **What it does:** Checks for closures which just call another function where
@ -74,7 +76,10 @@ impl<'tcx> LateLintPass<'tcx> for EtaReduction {
match expr.kind {
ExprKind::Call(_, args) | ExprKind::MethodCall(_, _, args, _) => {
for arg in args {
check_closure(cx, arg)
// skip `foo(macro!())`
if arg.span.ctxt() == expr.span.ctxt() {
check_closure(cx, arg)
}
}
},
_ => (),
@ -87,6 +92,23 @@ fn check_closure(cx: &LateContext<'_>, expr: &Expr<'_>) {
let body = cx.tcx.hir().body(eid);
let ex = &body.value;
if ex.span.ctxt() != expr.span.ctxt() {
if let Some(VecArgs::Vec(&[])) = higher::vec_macro(cx, ex) {
// replace `|| vec![]` with `Vec::new`
span_lint_and_sugg(
cx,
REDUNDANT_CLOSURE,
expr.span,
"redundant closure found",
"remove closure as shown",
"std::vec::Vec::new".into(),
Applicability::MachineApplicable,
);
}
// skip `foo(|| macro!())`
return;
}
if_chain!(
if let ExprKind::Call(ref caller, ref args) = ex.kind;