You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

82 lines
1.7 KiB

  1. use crate::error::ShellError;
  2. use crate::prompt::PromptStyle;
  3. use once_cell::unsync::Lazy;
  4. mod cd;
  5. mod change_prompt;
  6. mod exit;
  7. mod pwd;
  8. pub struct BuiltinConfig {
  9. pub prompt_style: PromptStyle,
  10. }
  11. impl BuiltinConfig {
  12. pub fn new() -> Self {
  13. Self {
  14. prompt_style: PromptStyle::Default,
  15. }
  16. }
  17. }
  18. trait Builtin: Sync + Send {
  19. fn execute(&mut self, config: &mut BuiltinConfig, args: Vec<String>) -> Result<(), ShellError>;
  20. }
  21. const BUILTINS: Lazy<Vec<(&str, Box<dyn Builtin>)>> = Lazy::new(|| {
  22. vec![
  23. ("cd", Box::new(cd::Cd)),
  24. ("change-prompt", Box::new(change_prompt::ChangePrompt)),
  25. ("exit", Box::new(exit::Exit)),
  26. ("pwd", Box::new(pwd::Pwd)),
  27. ]
  28. });
  29. pub fn is_builtin(keyword: &str) -> bool {
  30. BUILTINS.iter().find(|(k, _)| k == &keyword).is_some()
  31. }
  32. #[allow(const_item_mutation)]
  33. pub fn execute_builtin(
  34. keyword: &str,
  35. config: &mut BuiltinConfig,
  36. args: Vec<String>,
  37. ) -> Result<(), ShellError> {
  38. if let Some(builtin) = BUILTINS
  39. .iter_mut()
  40. .find_map(|(k, c)| if k == &keyword { Some(c) } else { None })
  41. {
  42. builtin.execute(config, args)?
  43. }
  44. Ok(())
  45. }
  46. #[cfg(test)]
  47. mod tests {
  48. use super::*;
  49. #[test]
  50. fn test_is_builtin_exit() {
  51. assert_eq!(is_builtin("exit"), true);
  52. }
  53. #[test]
  54. fn test_is_builtin_cd() {
  55. assert_eq!(is_builtin("cd"), true);
  56. }
  57. #[test]
  58. fn test_is_builtin_pwd() {
  59. assert_eq!(is_builtin("pwd"), true);
  60. }
  61. #[test]
  62. fn test_is_builtin_change_prompt() {
  63. assert_eq!(is_builtin("change-prompt"), true);
  64. }
  65. #[test]
  66. fn test_is_builtin_notabuiltin() {
  67. assert_eq!(is_builtin("notabuiltin"), false)
  68. }
  69. }