diff --git a/src/command/builtins.rs b/src/command/builtins.rs index 18fd624..534d1f6 100644 --- a/src/command/builtins.rs +++ b/src/command/builtins.rs @@ -1,4 +1,5 @@ -use crate::error::print_error; +use crate::error; +use crate::error::CdError; use crate::exit_code::ExitCode; use std::env; @@ -18,10 +19,12 @@ pub(super) fn cd(args: &Vec) -> ExitCode { let exit_code: ExitCode; if path.is_some() { - let result = set_current_dir(path.unwrap()); + let path = path.unwrap(); + let result = set_current_dir(&path); if result.is_err() { - print_error("cd: no such file or directory"); + let error = CdError::new(&args[0]); + error::print(Box::new(error)); exit_code = ExitCode::new(2); } else { exit_code = ExitCode::success(); diff --git a/src/command/mod.rs b/src/command/mod.rs index 1c47613..2d15b19 100644 --- a/src/command/mod.rs +++ b/src/command/mod.rs @@ -2,7 +2,8 @@ mod builtins; pub mod command_builder; pub mod command_sequence; -use crate::error::print_error; +use crate::error; +use crate::error::CommandNotFoundError; use crate::exit_code::ExitCode; type BuiltinFunction = fn(&Vec) -> ExitCode; @@ -81,11 +82,8 @@ impl Command for UnixProgram { exit_code } else { - let message = format!( - "{}: command not found", - self.command.get_program().to_str().unwrap() - ); - print_error(message.as_str()); + let error = CommandNotFoundError::new(self.command.get_program().to_str().unwrap()); + error::print(Box::new(error)); ExitCode::not_found() } } diff --git a/src/error.rs b/src/error.rs index 56cdea4..069b750 100644 --- a/src/error.rs +++ b/src/error.rs @@ -1,9 +1,49 @@ use std::env; +use std::fmt; +use std::fmt::{Display, Formatter}; use std::path::Path; -pub fn print_error(message: &str) { +type Error = Box; + +pub struct CdError { + entry_name: String, +} + +impl CdError { + pub fn new(entry_name: &str) -> Self { + Self { + entry_name: String::from(entry_name), + } + } +} + +impl Display for CdError { + fn fmt(&self, f: &mut Formatter) -> fmt::Result { + write!(f, "cd: no such directory as '{}'", self.entry_name) + } +} + +pub struct CommandNotFoundError { + command: String, +} + +impl CommandNotFoundError { + pub fn new(command: &str) -> Self { + Self { + command: String::from(command), + } + } +} + +impl Display for CommandNotFoundError { + fn fmt(&self, f: &mut Formatter) -> fmt::Result { + write!(f, "{}: command not found", self.command) + } +} + +pub fn print(error: Error) { let name = env::args().next().unwrap_or(String::from("rash")); let name = Path::new(&name).file_name().unwrap().to_str().unwrap(); - eprintln!("{}: {}", name, message); + eprintln!("{}: {}", name, error); }