]> git.lizzy.rs Git - rust.git/blob - clippy_lints/src/redundant_field_names.rs
Merge pull request #3459 from flip1995/sugg_appl
[rust.git] / clippy_lints / src / redundant_field_names.rs
1 // Copyright 2014-2018 The Rust Project Developers. See the COPYRIGHT
2 // file at the top-level directory of this distribution.
3 //
4 // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
5 // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
6 // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
7 // option. This file may not be copied, modified, or distributed
8 // except according to those terms.
9
10
11 use crate::rustc::lint::{EarlyContext, EarlyLintPass, LintArray, LintPass};
12 use crate::rustc::{declare_tool_lint, lint_array};
13 use crate::rustc_errors::Applicability;
14 use crate::syntax::ast::*;
15 use crate::utils::{span_lint_and_sugg};
16
17 /// **What it does:** Checks for fields in struct literals where shorthands
18 /// could be used.
19 ///
20 /// **Why is this bad?** If the field and variable names are the same,
21 /// the field name is redundant.
22 ///
23 /// **Known problems:** None.
24 ///
25 /// **Example:**
26 /// ```rust
27 /// let bar: u8 = 123;
28 ///
29 /// struct Foo {
30 ///     bar: u8,
31 /// }
32 ///
33 /// let foo = Foo{ bar: bar }
34 /// ```
35 /// the last line can be simplified to
36 /// ```rust
37 /// let foo = Foo{ bar }
38 /// ```
39 declare_clippy_lint! {
40     pub REDUNDANT_FIELD_NAMES,
41     style,
42     "checks for fields in struct literals where shorthands could be used"
43 }
44
45 pub struct RedundantFieldNames;
46
47 impl LintPass for RedundantFieldNames {
48     fn get_lints(&self) -> LintArray {
49         lint_array!(REDUNDANT_FIELD_NAMES)
50     }
51 }
52
53 impl EarlyLintPass for RedundantFieldNames {
54     fn check_expr(&mut self, cx: &EarlyContext<'_>, expr: &Expr) {
55         if let ExprKind::Struct(_, ref fields, _) = expr.node {
56             for field in fields {
57                 if field.is_shorthand {
58                     continue;
59                 }
60                 if let ExprKind::Path(None, path) = &field.expr.node {
61                     if path.segments.len() == 1 && path.segments[0].ident == field.ident {
62                         span_lint_and_sugg(
63                             cx,
64                             REDUNDANT_FIELD_NAMES,
65                             field.span,
66                             "redundant field names in struct initialization",
67                             "replace it with",
68                             field.ident.to_string(),
69                             Applicability::MachineApplicable,
70                         );
71                     }
72                 }
73             }
74         }
75     }
76 }