scud 0.3.0

A secret library atm, woo woo.
use std::time::SystemTime;
use crate::{
    cli::Commit,
    commands::commit::{
        helpers::{
            get_remaining_subject_length,
            get_commit_type,
            get_scope,
            get_subject,
            get_body,
            get_breaking_changes,
            get_referenced_issues,
        },
        logging::log_commit_message
    },
    logging::general::log_execution_time,
};
use dialoguer::{
    FuzzySelect,
    theme::ColorfulTheme,
    Input,
    Confirm,
};
use colored::Colorize;

pub fn commit_command(commit_options: Commit, start_time: SystemTime) {

    let commit_standards_options = &[
      "Conventional Commit Standard",
      "Angular Commit Standard",
      "None"
    ];

    // TODO
    // section for confirming commit message, or wanting to restart commit process after showing proposed commit message
    // TODO look into maybe autobumping version number after commit
    // TODO look into generating CHANGELOG after commit
    // corresponding to commit type
    // i.e
    // breaking change, bump version number to next major
    // feat, bump version number to next minor version
    // anything else (refactor, test, docs, style, build, etc.), bump version number to next patch version

    // TODO check for global config file and if so, skip this step

    let selected_specification = FuzzySelect::with_theme(&ColorfulTheme::default())
        .with_prompt("Select a commit message specification")
        .default(0)
        .items(&commit_standards_options[..])
        .interact()
        .unwrap();

    let mut commit_message = String::new();

    match selected_specification {
        0 => {
            commit_message = commit_conventional_commit_standard(&commit_options);
        }
        1 => {
            commit_message = commit_conventional_commit_standard(&commit_options);
        }
        2 => {
            commit_message = commit_conventional_commit_standard(&commit_options);
        }
        _ => {
            println!("{}{}", "Error: ".red().bold(), "Invalid selection of commit specification.".italic());
        }
    }
}

fn commit_conventional_commit_standard(commit_options: &Commit) -> String {
    // TODO fix issues with scope and description being printed twice

    let commit_type = get_commit_type();
    let scope = get_scope();
    let subject = get_subject(&commit_type, &scope);
    let body = get_body();
    let breaking_changes = get_breaking_changes();
    let referenced_issues = get_referenced_issues();

    let mut commit_message = String::new();

    commit_message =
    match scope.len() {
        0 => format!("{commit_type}: {subject}\n\n{body}"),
        _ => format!("{commit_type}({scope}): {subject}\n\n{body}"),
    };

    commit_message = match breaking_changes.len() {
        0 => commit_message,
        _ => format!("{commit_message}\n\nBREAKING CHANGE: {breaking_changes}"),
    };

    commit_message = match referenced_issues.len() {
        0 => commit_message,
        _ => format!("{commit_message}\n\nRefs: {referenced_issues}"),
    };

    log_commit_message(commit_type, scope, subject, body, breaking_changes, referenced_issues);

    commit_message
}

fn commit_angular_commit_standard(commit_options: &Commit) -> String {
    "angular message".to_string()
}

fn commit_none(commit_options: &Commit) -> String {
    "none message".to_string()
}

// all message options support fuzzy select for user input allowing for
// enhanced user experience
// TODO
// Linting for your commit messages baked-in, but you can also extend
// them / add your own.
// Will also run a lint over your commit message to ensure it follows the commit standard similar to the JavaScript tool, commitlint.

// TODO look into git trailer format
// https://git-scm.com/docs/git-interpret-trailers