use cli_util::cd;
use cli_util::find;
use cli_util::grep;
use cli_util::ls;
use cli_util::working_directory;
use std::fs::File;
use std::io::{stdout, Write};
use users::{get_current_uid, get_user_by_uid};
use console::Style;
use dialoguer::{theme::ColorfulTheme, BasicHistory, Input};
use std::fs::OpenOptions;
pub fn main() -> Result<(), Box<dyn std::error::Error>> {
let user = get_user_by_uid(get_current_uid()).ok_or("User not found")?;
let username: &str = user.name().to_str().ok_or("Username not found")?;
let mut history = BasicHistory::new().max_entries(8).no_duplicates(true);
let mut redirection: String;
let theme = ColorfulTheme {
prompt_suffix: Style::new().bold().apply_to(">".to_string()),
success_suffix: Style::new().apply_to(">".to_string()),
..ColorfulTheme::default()
};
loop {
let cmd_entry = Input::<String>::with_theme(&theme)
.with_prompt(format!("{} {}", username, working_directory()?))
.history_with(&mut history)
.interact_text();
let mut cmd_str = cmd_entry?;
let mut handle: Box<dyn Write> = if let Some(i) = cmd_str.find(">>") {
redirection = cmd_str[i + 2..].to_string();
cmd_str = cmd_str[..i].to_string();
let file = OpenOptions::new()
.append(true) .create(true) .open(redirection)?;
Box::new(file)
} else if let Some(i) = cmd_str.find('>') {
redirection = cmd_str[i + 1..].to_string();
cmd_str = cmd_str[..i].to_string();
Box::new(File::create(redirection)?)
} else {
Box::new(stdout().lock())
};
let (cmd, arg) = cmd_str
.split_once(' ')
.unwrap_or_else(|| (cmd_str.trim(), ""));
match cmd {
"echo" => println!("{arg}"), "cd" => cd::cd(arg)?,
"cat" => cli_util::cat(arg, &mut handle)?, "ls" => ls::ls(arg, &mut handle)?, "find" => find::find(arg, &mut handle)?, "grep" => grep::grep(arg, &mut handle)?, "" => continue,
_ => {
println!("Command {cmd} not found");
continue;
}
}
handle.flush()?;
}
}