commitfmt 0.0.1

A git commit message formatter
Documentation
use clap::Parser;
use commitfmt::{format_commit_message, Config};
use std::fs;
use std::io::{self, Read, Write};
use std::path::PathBuf;
use std::process;

#[derive(Parser)]
#[command(name = "commitfmt")]
#[command(about = "A git commit message formatter", long_about = None)]
struct Cli {
    /// Input file (if not provided, reads from stdin)
    input: Option<PathBuf>,

    /// Config file path (if not provided, searches for .commitfmt.toml)
    #[arg(short, long)]
    config: Option<PathBuf>,
}

fn main() {
    let cli = Cli::parse();

    let config = if let Some(config_path) = cli.config {
        Config::load_from_file(&config_path).unwrap_or_else(|e| {
            eprintln!("Error loading config file: {}", e);
            process::exit(1);
        })
    } else {
        Config::discover()
    };

    let input = read_input(cli.input.as_ref()).unwrap_or_else(|e| {
        eprintln!("Error reading input: {}", e);
        process::exit(1);
    });

    let formatted = format_commit_message(&input, &config);

    if let Err(e) = write_output(cli.input.as_ref(), &formatted) {
        eprintln!("Error writing output: {}", e);
        process::exit(1);
    }
}

fn read_input(path: Option<&PathBuf>) -> io::Result<String> {
    match path {
        Some(file_path) => fs::read_to_string(file_path),
        None => {
            let mut buffer = String::new();
            io::stdin().read_to_string(&mut buffer)?;
            Ok(buffer)
        }
    }
}

fn write_output(path: Option<&PathBuf>, content: &str) -> io::Result<()> {
    match path {
        Some(file_path) => {
            fs::write(file_path, content)?;
            println!("Formatted: {}", file_path.display());
            Ok(())
        }
        None => {
            print!("{}", content);
            io::stdout().flush()?;
            Ok(())
        }
    }
}