aboutsummaryrefslogtreecommitdiff
path: root/bin
diff options
context:
space:
mode:
Diffstat (limited to 'bin')
-rw-r--r--bin/Cargo.toml2
-rw-r--r--bin/src/config.rs4
-rw-r--r--bin/src/fix/single.rs23
-rw-r--r--bin/src/main.rs25
4 files changed, 31 insertions, 23 deletions
diff --git a/bin/Cargo.toml b/bin/Cargo.toml
index 481217a..971fb47 100644
--- a/bin/Cargo.toml
+++ b/bin/Cargo.toml
@@ -1,6 +1,6 @@
1[package] 1[package]
2name = "statix" 2name = "statix"
3version = "0.2.0" 3version = "0.2.2"
4edition = "2018" 4edition = "2018"
5license = "MIT" 5license = "MIT"
6 6
diff --git a/bin/src/config.rs b/bin/src/config.rs
index c856a59..79bed35 100644
--- a/bin/src/config.rs
+++ b/bin/src/config.rs
@@ -77,8 +77,8 @@ impl Fix {
77#[derive(Clap, Debug)] 77#[derive(Clap, Debug)]
78pub struct Single { 78pub struct Single {
79 /// File to run single-fix on 79 /// File to run single-fix on
80 #[clap(default_value = ".", parse(from_os_str))] 80 #[clap(parse(from_os_str))]
81 pub target: PathBuf, 81 pub target: Option<PathBuf>,
82 82
83 /// Position to attempt a fix at 83 /// Position to attempt a fix at
84 #[clap(short, long, parse(try_from_str = parse_line_col))] 84 #[clap(short, long, parse(try_from_str = parse_line_col))]
diff --git a/bin/src/fix/single.rs b/bin/src/fix/single.rs
index c09c710..4d492f8 100644
--- a/bin/src/fix/single.rs
+++ b/bin/src/fix/single.rs
@@ -15,7 +15,7 @@ fn pos_to_byte(line: usize, col: usize, src: &str) -> Result<TextSize, SingleFix
15 for (l, _) in src 15 for (l, _) in src
16 .split_inclusive('\n') 16 .split_inclusive('\n')
17 .zip(1..) 17 .zip(1..)
18 .take_while(|(_, i)| i < &line) 18 .take_while(|(_, i)| *i < line)
19 { 19 {
20 byte += TextSize::of(l); 20 byte += TextSize::of(l);
21 } 21 }
@@ -29,7 +29,6 @@ fn pos_to_byte(line: usize, col: usize, src: &str) -> Result<TextSize, SingleFix
29} 29}
30 30
31fn find(offset: TextSize, src: &str) -> Result<Report, SingleFixErr> { 31fn find(offset: TextSize, src: &str) -> Result<Report, SingleFixErr> {
32 let offset = offset - TextSize::from(1u32);
33 // we don't really need the source to form a completely parsed tree 32 // we don't really need the source to form a completely parsed tree
34 let parsed = rnix::parse(src); 33 let parsed = rnix::parse(src);
35 34
@@ -38,22 +37,18 @@ fn find(offset: TextSize, src: &str) -> Result<Report, SingleFixErr> {
38 .preorder_with_tokens() 37 .preorder_with_tokens()
39 .filter_map(|event| match event { 38 .filter_map(|event| match event {
40 WalkEvent::Enter(child) => { 39 WalkEvent::Enter(child) => {
41 if child.text_range().start() == offset { 40 LINTS.get(&child.kind()).map(|rules| {
42 LINTS.get(&child.kind()).map(|rules| { 41 rules
43 rules 42 .iter()
44 .iter() 43 .filter_map(|rule| rule.validate(&child))
45 .filter_map(|rule| rule.validate(&child)) 44 .filter(|report| report.total_suggestion_range().is_some())
46 .filter(|report| report.total_suggestion_range().is_some()) 45 .next()
47 .next() 46 })
48 })
49 } else {
50 None
51 }
52 } 47 }
53 _ => None, 48 _ => None,
54 }) 49 })
55 .flatten() 50 .flatten()
56 .next() 51 .find(|report| report.total_diagnostic_range().unwrap().contains(offset))
57 .ok_or(SingleFixErr::NoOp) 52 .ok_or(SingleFixErr::NoOp)
58} 53}
59 54
diff --git a/bin/src/main.rs b/bin/src/main.rs
index 4063621..9e9c8ac 100644
--- a/bin/src/main.rs
+++ b/bin/src/main.rs
@@ -4,7 +4,7 @@ mod fix;
4mod lint; 4mod lint;
5mod traits; 5mod traits;
6 6
7use std::io; 7use std::io::{self, BufRead};
8 8
9use crate::{ 9use crate::{
10 err::{FixErr, SingleFixErr, StatixErr}, 10 err::{FixErr, SingleFixErr, StatixErr},
@@ -55,15 +55,26 @@ fn _main() -> Result<(), StatixErr> {
55 } 55 }
56 } 56 }
57 } 57 }
58 // FIXME: this block nasty, configure in/out streams in `impl Single` maybe
58 SubCommand::Single(single_config) => { 59 SubCommand::Single(single_config) => {
59 let path = single_config.target; 60 let src = if let Some(path) = &single_config.target {
60 let src = std::fs::read_to_string(&path).map_err(SingleFixErr::InvalidPath)?; 61 std::fs::read_to_string(&path).map_err(SingleFixErr::InvalidPath)?
62 } else {
63 io::stdin().lock().lines().map(|l| l.unwrap()).collect::<Vec<String>>().join("\n")
64 };
65
66 let path_id = if let Some(path) = &single_config.target {
67 path.display().to_string()
68 } else {
69 "<unknown>".to_owned()
70 };
71
61 let (line, col) = single_config.position; 72 let (line, col) = single_config.position;
62 let single_fix_result = fix::single(line, col, &src)?; 73 let single_fix_result = fix::single(line, col, &src)?;
63 if single_config.diff_only { 74 if single_config.diff_only {
64 let text_diff = TextDiff::from_lines(src.as_str(), &single_fix_result.src); 75 let text_diff = TextDiff::from_lines(src.as_str(), &single_fix_result.src);
65 let old_file = format!("{}", path.display()); 76 let old_file = format!("{}", path_id);
66 let new_file = format!("{} [fixed]", path.display()); 77 let new_file = format!("{} [fixed]", path_id);
67 println!( 78 println!(
68 "{}", 79 "{}",
69 text_diff 80 text_diff
@@ -71,9 +82,11 @@ fn _main() -> Result<(), StatixErr> {
71 .context_radius(4) 82 .context_radius(4)
72 .header(&old_file, &new_file) 83 .header(&old_file, &new_file)
73 ); 84 );
74 } else { 85 } else if let Some(path) = single_config.target {
75 std::fs::write(&path, &*single_fix_result.src) 86 std::fs::write(&path, &*single_fix_result.src)
76 .map_err(SingleFixErr::InvalidPath)?; 87 .map_err(SingleFixErr::InvalidPath)?;
88 } else {
89 print!("{}", &*single_fix_result.src)
77 } 90 }
78 } 91 }
79 } 92 }