Skip to content

Commit

Permalink
WIP: Tryouts on a fix command.
Browse files Browse the repository at this point in the history
  • Loading branch information
o0Ignition0o committed Jan 13, 2020
1 parent 7a80947 commit 18e05d3
Show file tree
Hide file tree
Showing 7 changed files with 75 additions and 1 deletion.
2 changes: 2 additions & 0 deletions cargo-scout-lib/src/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,4 +18,6 @@ pub enum Error {
Io(#[from] std::io::Error),
#[error("Git error: {0}")]
Git(#[from] git2::Error),
#[error("The provided command is invalid.")]
InvalidCommand,
}
5 changes: 5 additions & 0 deletions cargo-scout-lib/src/healer/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
use crate::linter::Lint;

pub trait Healer {
fn heal(&self, lints: Vec<Lint>) -> Result<(), crate::error::Error>;
}
1 change: 1 addition & 0 deletions cargo-scout-lib/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
pub mod config;
pub mod error;
pub mod healer;
pub mod linter;
pub mod scout;
pub mod vcs;
Expand Down
3 changes: 2 additions & 1 deletion cargo-scout-lib/src/linter/mod.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
use serde::Serialize;
use std::path::PathBuf;

pub mod clippy;
Expand All @@ -21,7 +22,7 @@ pub struct Lint {
}

/// A `Location` has a file name, a start and an end line
#[derive(PartialEq, Clone, Debug)]
#[derive(Serialize, PartialEq, Clone, Debug)]
pub struct Location {
pub path: String,
pub lines: [u32; 2],
Expand Down
19 changes: 19 additions & 0 deletions cargo-scout-lib/src/linter/rustfmt.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use crate::error::Error;
use crate::healer::Healer;
use crate::linter::{Lint, Linter, Location};
use crate::utils::get_absolute_file_path;
use serde::Deserialize;
Expand All @@ -21,6 +22,24 @@ impl Linter for RustFmt {
}
}

impl Healer for RustFmt {
fn heal(&self, lints: Vec<Lint>) -> Result<(), crate::error::Error> {
Command::new("rustfmt").args(&[
"--unstable-features",
"--file-lines",
&lints_as_json(&lints)?,
"--skip-children",
"--edition=2018",
]);
Ok(())
}
}

fn lints_as_json(lints: &[Lint]) -> Result<String, crate::error::Error> {
let locations: Vec<Location> = lints.iter().map(|l| l.location.clone()).collect();
Ok(serde_json::to_string(&locations)?)
}

impl RustFmt {
fn command_parameters() -> Vec<&'static str> {
vec!["+nightly", "fmt", "--", "--emit", "json"]
Expand Down
21 changes: 21 additions & 0 deletions cargo-scout-lib/src/scout/mod.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use crate::config::*;
use crate::healer::Healer;
use crate::linter::{Lint, Linter};
use crate::vcs::*;
use std::path::PathBuf;
Expand Down Expand Up @@ -47,6 +48,26 @@ where
}
}

pub struct Fixer<H>
where
H: Healer,
{
medic: H,
}

impl<H> Fixer<H>
where
H: Healer,
{
pub fn new(medic: H) -> Self {
Self { medic }
}
pub fn run(&self, lints: Vec<Lint>) -> Result<(), crate::error::Error> {
println!("[Scout] - applying fixes");
self.medic.heal(lints)
}
}

fn diff_in_member(member: &PathBuf, sections: &[Section]) -> bool {
if let Some(m) = member.to_str() {
for s in sections {
Expand Down
25 changes: 25 additions & 0 deletions cargo-scout/src/main.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
use cargo_scout_lib::config::rust::CargoConfig;
use cargo_scout_lib::fixer::Fixer;
use cargo_scout_lib::linter::clippy::Clippy;
use cargo_scout_lib::linter::rustfmt::RustFmt;
use cargo_scout_lib::linter::Lint;
Expand All @@ -15,6 +16,12 @@ use structopt::StructOpt;
)]
enum Command {
Fmt(FmtOptions),
Fix(FixCommand),
Lint(LintOptions),
}

#[derive(StructOpt)]
enum FixCommand {
Lint(LintOptions),
}

Expand Down Expand Up @@ -74,11 +81,29 @@ struct LintOptions {
#[cfg_attr(tarpaulin, skip)]
fn main() -> Result<(), Error> {
match Command::from_args() {
Command::Fix(opts) => run_fix(opts),
Command::Fmt(opts) => run_fmt(opts),
Command::Lint(opts) => run_lint(opts),
}
}

#[cfg_attr(tarpaulin, skip)]
#[allow(irrefutable_let_patterns)]
fn run_fix(fix_command: FixCommand) -> Result<(), Error> {
if let FixCommand::Lint(opts) = fix_command {
let vcs = Git::with_target(opts.branch);
let config = CargoConfig::from_manifest_path(opts.cargo_toml)?;
let linter = RustFmt::default();

let scout = Scout::new(vcs, config, linter); // TODO: do not consume?
let relevant_lints = scout.run()?;
let fixer = RustFmt::default();
fixer.fix(relevant_lints)?
}

Err(Error::InvalidCommand)
}

#[cfg_attr(tarpaulin, skip)]
fn run_lint(opts: LintOptions) -> Result<(), Error> {
let fail_if_errors = opts.without_error;
Expand Down

0 comments on commit 18e05d3

Please sign in to comment.