#[macro_use]
extern crate log;

use std::env;
use std::io::stdout;
use std::path::{Path, PathBuf};
use std::process::Command;
use std::str::FromStr;

use getopts::{Matches, Options};
use rustfmt_nightly as rustfmt;

use crate::rustfmt::{load_config, CliOptions, FormatReportFormatterBuilder, Input, Session};

fn prune_files(files: Vec<&str>) -> Vec<&str> {
    let prefixes: Vec<_> = files
        .iter()
        .filter(|f| f.ends_with("mod.rs") || f.ends_with("lib.rs"))
        .map(|f| &f[..f.len() - 6])
        .collect();

    let mut pruned_prefixes = vec![];
    for p1 in prefixes {
        if p1.starts_with("src/bin/") || pruned_prefixes.iter().all(|p2| !p1.starts_with(p2)) {
            pruned_prefixes.push(p1);
        }
    }
    debug!("prefixes: {:?}", pruned_prefixes);

    files
        .into_iter()
        .filter(|f| {
            if f.ends_with("mod.rs") || f.ends_with("lib.rs") || f.starts_with("src/bin/") {
                return true;
            }
            pruned_prefixes.iter().all(|pp| !f.starts_with(pp))
        })
        .collect()
}

fn git_diff(commits: &str) -> String {
    let mut cmd = Command::new("git");
    cmd.arg("diff");
    if commits != "0" {
        cmd.arg(format!("HEAD~{}", commits));
    }
    let output = cmd.output().expect("Couldn't execute `git diff`");
    String::from_utf8_lossy(&output.stdout).into_owned()
}

fn get_files(input: &str) -> Vec<&str> {
    input
        .lines()
        .filter(|line| line.starts_with("+++ b/") && line.ends_with(".rs"))
        .map(|line| &line[6..])
        .collect()
}

fn fmt_files(files: &[&str]) -> i32 {
    let (config, _) =
        load_config::<NullOptions>(Some(Path::new(".")), None).expect("couldn't load config");

    let mut exit_code = 0;
    let mut out = stdout();
    let mut session = Session::new(config, Some(&mut out));
    for file in files {
        let report = session.format(Input::File(PathBuf::from(file))).unwrap();
        if report.has_warnings() {
            eprintln!("{}", FormatReportFormatterBuilder::new(&report).build());
        }
        if !session.has_no_errors() {
            exit_code = 1;
        }
    }
    exit_code
}

struct NullOptions;

impl CliOptions for NullOptions {
    fn apply_to(self, _: &mut rustfmt::Config) {
        unreachable!();
    }
    fn config_path(&self) -> Option<&Path> {
        unreachable!();
    }
}

fn uncommitted_files() -> Vec<String> {
    let mut cmd = Command::new("git");
    cmd.arg("ls-files");
    cmd.arg("--others");
    cmd.arg("--modified");
    cmd.arg("--exclude-standard");
    let output = cmd.output().expect("Couldn't execute Git");
    let stdout = String::from_utf8_lossy(&output.stdout);
    stdout
        .lines()
        .filter(|s| s.ends_with(".rs"))
        .map(std::borrow::ToOwned::to_owned)
        .collect()
}

fn check_uncommitted() {
    let uncommitted = uncommitted_files();
    debug!("uncommitted files: {:?}", uncommitted);
    if !uncommitted.is_empty() {
        println!("Found untracked changes:");
        for f in &uncommitted {
            println!("  {}", f);
        }
        println!("Commit your work, or run with `-u`.");
        println!("Exiting.");
        std::process::exit(1);
    }
}

fn make_opts() -> Options {
    let mut opts = Options::new();
    opts.optflag("h", "help", "show this message");
    opts.optflag("c", "check", "check only, don't format (unimplemented)");
    opts.optflag("u", "uncommitted", "format uncommitted files");
    opts
}

struct Config {
    commits: String,
    uncommitted: bool,
}

impl Config {
    fn from_args(matches: &Matches, opts: &Options) -> Config {
        // `--help` display help message and quit
        if matches.opt_present("h") {
            let message = format!(
                "\nusage: {} <commits> [options]\n\n\
                 commits: number of commits to format, default: 1",
                env::args_os().next().unwrap().to_string_lossy()
            );
            println!("{}", opts.usage(&message));
            std::process::exit(0);
        }

        let mut config = Config {
            commits: "1".to_owned(),
            uncommitted: false,
        };

        if matches.opt_present("c") {
            unimplemented!();
        }

        if matches.opt_present("u") {
            config.uncommitted = true;
        }

        if matches.free.len() > 1 {
            panic!("unknown arguments, use `-h` for usage");
        }
        if matches.free.len() == 1 {
            let commits = matches.free[0].trim();
            if u32::from_str(commits).is_err() {
                panic!("Couldn't parse number of commits");
            }
            config.commits = commits.to_owned();
        }

        config
    }
}

fn main() {
    env_logger::init();

    let opts = make_opts();
    let matches = opts
        .parse(env::args().skip(1))
        .expect("Couldn't parse command line");
    let config = Config::from_args(&matches, &opts);

    if !config.uncommitted {
        check_uncommitted();
    }

    let stdout = git_diff(&config.commits);
    let files = get_files(&stdout);
    debug!("files: {:?}", files);
    let files = prune_files(files);
    debug!("pruned files: {:?}", files);
    let exit_code = fmt_files(&files);
    std::process::exit(exit_code);
}
