Run rustfmt on clippy_dev

This commit is contained in:
flip1995 2018-11-27 21:13:08 +01:00
parent 3befd86967
commit f9c0e2a4cb
No known key found for this signature in database
GPG key ID: E8E897A5870E41C2
2 changed files with 181 additions and 115 deletions

View file

@ -7,30 +7,35 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
#![allow(clippy::default_hash_types)]
use itertools::Itertools;
use lazy_static::lazy_static;
use regex::Regex;
use walkdir::WalkDir;
use std::collections::HashMap;
use std::ffi::OsStr;
use std::fs;
use std::io::prelude::*;
use walkdir::WalkDir;
lazy_static! {
static ref DEC_CLIPPY_LINT_RE: Regex = Regex::new(r#"(?x)
static ref DEC_CLIPPY_LINT_RE: Regex = Regex::new(
r#"(?x)
declare_clippy_lint!\s*[\{(]\s*
pub\s+(?P<name>[A-Z_][A-Z_0-9]*)\s*,\s*
(?P<cat>[a-z_]+)\s*,\s*
"(?P<desc>(?:[^"\\]+|\\(?s).(?-s))*)"\s*[})]
"#).unwrap();
static ref DEC_DEPRECATED_LINT_RE: Regex = Regex::new(r#"(?x)
"#
)
.unwrap();
static ref DEC_DEPRECATED_LINT_RE: Regex = Regex::new(
r#"(?x)
declare_deprecated_lint!\s*[{(]\s*
pub\s+(?P<name>[A-Z_][A-Z_0-9]*)\s*,\s*
"(?P<desc>(?:[^"\\]+|\\(?s).(?-s))*)"\s*[})]
"#).unwrap();
"#
)
.unwrap();
static ref NL_ESCAPE_RE: Regex = Regex::new(r#"\\\n\s*"#).unwrap();
pub static ref DOCS_LINK: String = "https://rust-lang.github.io/rust-clippy/master/index.html".to_string();
}
@ -63,7 +68,10 @@ impl Lint {
/// Returns the lints in a HashMap, grouped by the different lint groups
pub fn by_lint_group(lints: &[Self]) -> HashMap<String, Vec<Self>> {
lints.iter().map(|lint| (lint.group.to_string(), lint.clone())).into_group_map()
lints
.iter()
.map(|lint| (lint.group.to_string(), lint.clone()))
.into_group_map()
}
pub fn is_internal(&self) -> bool {
@ -73,7 +81,8 @@ impl Lint {
/// Generates the Vec items for `register_lint_group` calls in `clippy_lints/src/lib.rs`.
pub fn gen_lint_group_list(lints: Vec<Lint>) -> Vec<String> {
lints.into_iter()
lints
.into_iter()
.filter_map(|l| {
if l.is_internal() || l.deprecation.is_some() {
None
@ -86,14 +95,17 @@ pub fn gen_lint_group_list(lints: Vec<Lint>) -> Vec<String> {
/// Generates the `pub mod module_name` list in `clippy_lints/src/lib.rs`.
pub fn gen_modules_list(lints: Vec<Lint>) -> Vec<String> {
lints.into_iter()
lints
.into_iter()
.filter_map(|l| {
if l.is_internal() || l.deprecation.is_some() { None } else { Some(l.module) }
if l.is_internal() || l.deprecation.is_some() {
None
} else {
Some(l.module)
}
})
.unique()
.map(|module| {
format!("pub mod {};", module)
})
.map(|module| format!("pub mod {};", module))
.sorted()
}
@ -109,27 +121,23 @@ pub fn gen_changelog_lint_list(lints: Vec<Lint>) -> Vec<String> {
} else {
Some(format!("[`{}`]: {}#{}", l.name, DOCS_LINK.clone(), l.name))
}
}).collect()
})
.collect()
}
/// Generates the `register_removed` code in `./clippy_lints/src/lib.rs`.
pub fn gen_deprecated(lints: &[Lint]) -> Vec<String> {
itertools::flatten(
lints
.iter()
.filter_map(|l| {
itertools::flatten(lints.iter().filter_map(|l| {
l.clone().deprecation.and_then(|depr_text| {
Some(
vec![
Some(vec![
" store.register_removed(".to_string(),
format!(" \"{}\",", l.name),
format!(" \"{}\",", depr_text),
" );".to_string()
]
)
" );".to_string(),
])
})
})
).collect()
}))
.collect()
}
/// Gathers all files in `src/clippy_lints` and gathers all lints inside
@ -145,7 +153,14 @@ fn gather_from_file(dir_entry: &walkdir::DirEntry) -> impl Iterator<Item=Lint> {
// If the lints are stored in mod.rs, we get the module name from
// the containing directory:
if filename == "mod" {
filename = dir_entry.path().parent().unwrap().file_stem().unwrap().to_str().unwrap()
filename = dir_entry
.path()
.parent()
.unwrap()
.file_stem()
.unwrap()
.to_str()
.unwrap()
}
parse_contents(&content, filename)
}
@ -184,15 +199,27 @@ pub struct FileChange {
///
/// See `replace_region_in_text` for documentation of the other options.
#[allow(clippy::expect_fun_call)]
pub fn replace_region_in_file<F>(path: &str, start: &str, end: &str, replace_start: bool, write_back: bool, replacements: F) -> FileChange where F: Fn() -> Vec<String> {
pub fn replace_region_in_file<F>(
path: &str,
start: &str,
end: &str,
replace_start: bool,
write_back: bool,
replacements: F,
) -> FileChange
where
F: Fn() -> Vec<String>,
{
let mut f = fs::File::open(path).expect(&format!("File not found: {}", path));
let mut contents = String::new();
f.read_to_string(&mut contents).expect("Something went wrong reading the file");
f.read_to_string(&mut contents)
.expect("Something went wrong reading the file");
let file_change = replace_region_in_text(&contents, start, end, replace_start, replacements);
if write_back {
let mut f = fs::File::create(path).expect(&format!("File not found: {}", path));
f.write_all(file_change.new_lines.as_bytes()).expect("Unable to write file");
f.write_all(file_change.new_lines.as_bytes())
.expect("Unable to write file");
// Ensure we write the changes with a trailing newline so that
// the file has the proper line endings.
f.write_all(b"\n").expect("Unable to write file");
@ -205,10 +232,10 @@ pub fn replace_region_in_file<F>(path: &str, start: &str, end: &str, replace_sta
/// * `text` is the input text on which you want to perform the replacement
/// * `start` is a `&str` that describes the delimiter line before the region you want to replace.
/// As the `&str` will be converted to a `Regex`, this can contain regex syntax, too.
/// * `end` is a `&str` that describes the delimiter line until where the replacement should
/// happen. As the `&str` will be converted to a `Regex`, this can contain regex syntax, too.
/// * If `replace_start` is true, the `start` delimiter line is replaced as well.
/// The `end` delimiter line is never replaced.
/// * `end` is a `&str` that describes the delimiter line until where the replacement should happen.
/// As the `&str` will be converted to a `Regex`, this can contain regex syntax, too.
/// * If `replace_start` is true, the `start` delimiter line is replaced as well. The `end`
/// delimiter line is never replaced.
/// * `replacements` is a closure that has to return a `Vec<String>` which contains the new text.
///
/// If you want to perform the replacement on files instead of already parsed text,
@ -218,18 +245,16 @@ pub fn replace_region_in_file<F>(path: &str, start: &str, end: &str, replace_sta
///
/// ```
/// let the_text = "replace_start\nsome text\nthat will be replaced\nreplace_end";
/// let result = clippy_dev::replace_region_in_text(
/// the_text,
/// r#"replace_start"#,
/// r#"replace_end"#,
/// false,
/// || {
/// let result = clippy_dev::replace_region_in_text(the_text, r#"replace_start"#, r#"replace_end"#, false, || {
/// vec!["a different".to_string(), "text".to_string()]
/// }
/// ).new_lines;
/// })
/// .new_lines;
/// assert_eq!("replace_start\na different\ntext\nreplace_end", result);
/// ```
pub fn replace_region_in_text<F>(text: &str, start: &str, end: &str, replace_start: bool, replacements: F) -> FileChange where F: Fn() -> Vec<String> {
pub fn replace_region_in_text<F>(text: &str, start: &str, end: &str, replace_start: bool, replacements: F) -> FileChange
where
F: Fn() -> Vec<String>,
{
let lines = text.lines();
let mut in_old_region = false;
let mut found = false;
@ -264,7 +289,7 @@ pub fn replace_region_in_text<F>(text: &str, start: &str, end: &str, replace_sta
FileChange {
changed: lines.ne(new_lines.clone()),
new_lines: new_lines.join("\n")
new_lines: new_lines.join("\n"),
}
}
@ -291,7 +316,9 @@ declare_deprecated_lint! {
"`assert!()` will be more flexible with RFC 2011"
}
"#,
"module_name").collect();
"module_name",
)
.collect();
let expected = vec![
Lint::new("ptr_arg", "style", "really long text", None, "module_name"),
@ -301,7 +328,7 @@ declare_deprecated_lint! {
"Deprecated",
"`assert!()` will be more flexible with RFC 2011",
Some("`assert!()` will be more flexible with RFC 2011"),
"module_name"
"module_name",
),
];
assert_eq!(expected, result);
@ -312,7 +339,7 @@ fn test_replace_region() {
let text = "\nabc\n123\n789\ndef\nghi";
let expected = FileChange {
changed: true,
new_lines: "\nabc\nhello world\ndef\nghi".to_string()
new_lines: "\nabc\nhello world\ndef\nghi".to_string(),
};
let result = replace_region_in_text(text, r#"^\s*abc$"#, r#"^\s*def"#, false, || {
vec!["hello world".to_string()]
@ -325,7 +352,7 @@ fn test_replace_region_with_start() {
let text = "\nabc\n123\n789\ndef\nghi";
let expected = FileChange {
changed: true,
new_lines: "\nhello world\ndef\nghi".to_string()
new_lines: "\nhello world\ndef\nghi".to_string(),
};
let result = replace_region_in_text(text, r#"^\s*abc$"#, r#"^\s*def"#, true, || {
vec!["hello world".to_string()]
@ -338,11 +365,9 @@ fn test_replace_region_no_changes() {
let text = "123\n456\n789";
let expected = FileChange {
changed: false,
new_lines: "123\n456\n789".to_string()
new_lines: "123\n456\n789".to_string(),
};
let result = replace_region_in_text(text, r#"^\s*123$"#, r#"^\s*456"#, false, || {
vec![]
});
let result = replace_region_in_text(text, r#"^\s*123$"#, r#"^\s*456"#, false, || vec![]);
assert_eq!(expected, result);
}
@ -352,11 +377,15 @@ fn test_usable_lints() {
Lint::new("should_assert_eq", "Deprecated", "abc", Some("Reason"), "module_name"),
Lint::new("should_assert_eq2", "Not Deprecated", "abc", None, "module_name"),
Lint::new("should_assert_eq2", "internal", "abc", None, "module_name"),
Lint::new("should_assert_eq2", "internal_style", "abc", None, "module_name")
];
let expected = vec![
Lint::new("should_assert_eq2", "Not Deprecated", "abc", None, "module_name")
Lint::new("should_assert_eq2", "internal_style", "abc", None, "module_name"),
];
let expected = vec![Lint::new(
"should_assert_eq2",
"Not Deprecated",
"abc",
None,
"module_name",
)];
assert_eq!(expected, Lint::usable_lints(lints.into_iter()).collect::<Vec<Lint>>());
}
@ -368,13 +397,17 @@ fn test_by_lint_group() {
Lint::new("incorrect_match", "group1", "abc", None, "module_name"),
];
let mut expected: HashMap<String, Vec<Lint>> = HashMap::new();
expected.insert("group1".to_string(), vec![
expected.insert(
"group1".to_string(),
vec![
Lint::new("should_assert_eq", "group1", "abc", None, "module_name"),
Lint::new("incorrect_match", "group1", "abc", None, "module_name"),
]);
expected.insert("group2".to_string(), vec![
Lint::new("should_assert_eq2", "group2", "abc", None, "module_name")
]);
],
);
expected.insert(
"group2".to_string(),
vec![Lint::new("should_assert_eq2", "group2", "abc", None, "module_name")],
);
assert_eq!(expected, Lint::by_lint_group(&lints));
}
@ -387,7 +420,7 @@ fn test_gen_changelog_lint_list() {
];
let expected = vec![
format!("[`should_assert_eq`]: {}#should_assert_eq", DOCS_LINK.to_string()),
format!("[`should_assert_eq2`]: {}#should_assert_eq2", DOCS_LINK.to_string())
format!("[`should_assert_eq2`]: {}#should_assert_eq2", DOCS_LINK.to_string()),
];
assert_eq!(expected, gen_changelog_lint_list(lints));
}
@ -395,9 +428,21 @@ fn test_gen_changelog_lint_list() {
#[test]
fn test_gen_deprecated() {
let lints = vec![
Lint::new("should_assert_eq", "group1", "abc", Some("has been superseeded by should_assert_eq2"), "module_name"),
Lint::new("another_deprecated", "group2", "abc", Some("will be removed"), "module_name"),
Lint::new("should_assert_eq2", "group2", "abc", None, "module_name")
Lint::new(
"should_assert_eq",
"group1",
"abc",
Some("has been superseeded by should_assert_eq2"),
"module_name",
),
Lint::new(
"another_deprecated",
"group2",
"abc",
Some("will be removed"),
"module_name",
),
Lint::new("should_assert_eq2", "group2", "abc", None, "module_name"),
];
let expected: Vec<String> = vec![
" store.register_removed(",
@ -407,8 +452,11 @@ fn test_gen_deprecated() {
" store.register_removed(",
" \"another_deprecated\",",
" \"will be removed\",",
" );"
].into_iter().map(String::from).collect();
" );",
]
.into_iter()
.map(String::from)
.collect();
assert_eq!(expected, gen_deprecated(&lints));
}

View file

@ -7,7 +7,6 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
extern crate clap;
extern crate clippy_dev;
extern crate regex;
@ -18,29 +17,31 @@ use clippy_dev::*;
#[derive(PartialEq)]
enum UpdateMode {
Check,
Change
Change,
}
fn main() {
let matches = App::new("Clippy developer tooling")
.subcommand(
SubCommand::with_name("update_lints")
.about("Makes sure that:\n \
.about(
"Makes sure that:\n \
* the lint count in README.md is correct\n \
* the changelog contains markdown link references at the bottom\n \
* all lint groups include the correct lints\n \
* lint modules in `clippy_lints/*` are visible in `src/lib.rs` via `pub mod`\n \
* all lints are registered in the lint store")
.arg(
Arg::with_name("print-only")
.long("print-only")
.help("Print a table of lints to STDOUT. This does not include deprecated and internal lints. (Does not modify any files)")
* all lints are registered in the lint store",
)
.arg(Arg::with_name("print-only").long("print-only").help(
"Print a table of lints to STDOUT. \
This does not include deprecated and internal lints. \
(Does not modify any files)",
))
.arg(
Arg::with_name("check")
.long("check")
.help("Checks that util/dev update_lints has been run. Used on CI."),
)
),
)
.get_matches();
@ -62,13 +63,21 @@ fn print_lints() {
let grouped_by_lint_group = Lint::by_lint_group(&usable_lints);
for (lint_group, mut lints) in grouped_by_lint_group {
if lint_group == "Deprecated" { continue; }
if lint_group == "Deprecated" {
continue;
}
println!("\n## {}", lint_group);
lints.sort_by_key(|l| l.name.clone());
for lint in lints {
println!("* [{}]({}#{}) ({})", lint.name, clippy_dev::DOCS_LINK.clone(), lint.name, lint.desc);
println!(
"* [{}]({}#{}) ({})",
lint.name,
clippy_dev::DOCS_LINK.clone(),
lint.name,
lint.desc
);
}
}
@ -99,8 +108,9 @@ fn update_lints(update_mode: &UpdateMode) {
"<!-- end autogenerated links to lint list -->",
false,
update_mode == &UpdateMode::Change,
|| { gen_changelog_lint_list(lint_list.clone()) }
).changed;
|| gen_changelog_lint_list(lint_list.clone()),
)
.changed;
file_change |= replace_region_in_file(
"../clippy_lints/src/lib.rs",
@ -108,8 +118,9 @@ fn update_lints(update_mode: &UpdateMode) {
"end deprecated lints",
false,
update_mode == &UpdateMode::Change,
|| { gen_deprecated(&lint_list) }
).changed;
|| gen_deprecated(&lint_list),
)
.changed;
file_change |= replace_region_in_file(
"../clippy_lints/src/lib.rs",
@ -117,8 +128,9 @@ fn update_lints(update_mode: &UpdateMode) {
"end lints modules",
false,
update_mode == &UpdateMode::Change,
|| { gen_modules_list(lint_list.clone()) }
).changed;
|| gen_modules_list(lint_list.clone()),
)
.changed;
// Generate lists of lints in the clippy::all lint group
file_change |= replace_region_in_file(
@ -129,16 +141,18 @@ fn update_lints(update_mode: &UpdateMode) {
update_mode == &UpdateMode::Change,
|| {
// clippy::all should only include the following lint groups:
let all_group_lints = usable_lints.clone().into_iter().filter(|l| {
l.group == "correctness" ||
l.group == "style" ||
l.group == "complexity" ||
l.group == "perf"
}).collect();
let all_group_lints = usable_lints
.clone()
.into_iter()
.filter(|l| {
l.group == "correctness" || l.group == "style" || l.group == "complexity" || l.group == "perf"
})
.collect();
gen_lint_group_list(all_group_lints)
}
).changed;
},
)
.changed;
// Generate the list of lints for all other lint groups
for (lint_group, lints) in Lint::by_lint_group(&usable_lints) {
@ -148,12 +162,16 @@ fn update_lints(update_mode: &UpdateMode) {
r#"\]\);"#,
false,
update_mode == &UpdateMode::Change,
|| { gen_lint_group_list(lints.clone()) }
).changed;
|| gen_lint_group_list(lints.clone()),
)
.changed;
}
if update_mode == &UpdateMode::Check && file_change {
println!("Not all lints defined properly. Please run `util/dev update_lints` to make sure all lints are defined properly.");
println!(
"Not all lints defined properly. \
Please run `util/dev update_lints` to make sure all lints are defined properly."
);
std::process::exit(1);
}
}