From ce1be977d480b3bced075dedf0cac7d9a95e76ef Mon Sep 17 00:00:00 2001 From: Caznix Date: Mon, 2 Dec 2024 15:43:39 -0500 Subject: [PATCH] replace reedline with rustyline --- engine/Cargo.toml | 2 +- engine/src/core/repl/repl.rs | 83 +++++++++++------------------------- engine/src/main.rs | 6 +-- 3 files changed, 29 insertions(+), 62 deletions(-) diff --git a/engine/Cargo.toml b/engine/Cargo.toml index 8032f37..a635866 100644 --- a/engine/Cargo.toml +++ b/engine/Cargo.toml @@ -12,8 +12,8 @@ lazy_static = "1.5.0" log = "0.4.22" once_cell = "1.20.2" parking_lot = "0.12.3" -reedline = "0.37.0" regex = "1.11.1" +rustyline = "15.0.0" thiserror = "2.0.3" tokio = { version = "1.41.1", features = ["macros", "rt", "rt-multi-thread"] } wgpu = "23.0.1" diff --git a/engine/src/core/repl/repl.rs b/engine/src/core/repl/repl.rs index 673d4ea..8ac6710 100644 --- a/engine/src/core/repl/repl.rs +++ b/engine/src/core/repl/repl.rs @@ -1,7 +1,10 @@ use super::{commands, Callable, COMMAND_LIST}; +use anyhow::Result; use chrono::Local; -use reedline::{Prompt, Reedline, Signal}; +use colored::Colorize; +use log::debug; use regex::Regex; +use rustyline::DefaultEditor; fn register_commands() { COMMAND_LIST.add_command( @@ -44,46 +47,7 @@ fn register_commands() { COMMAND_LIST.add_alias("clear".to_string(), "cls".to_string()); } -struct ZPrompt { - left_text: String, - right_text: String, -} -impl Prompt for ZPrompt { - fn render_prompt_left(&self) -> std::borrow::Cow { - std::borrow::Cow::Borrowed(&self.left_text) - } - - fn render_prompt_right(&self) -> std::borrow::Cow { - std::borrow::Cow::Borrowed(&self.right_text) - } - - fn render_prompt_history_search_indicator( - &self, - _history_search: reedline::PromptHistorySearch, - ) -> std::borrow::Cow { - std::borrow::Cow::Borrowed("") - } - - fn render_prompt_indicator( - &self, - prompt_mode: reedline::PromptEditMode, - ) -> std::borrow::Cow { - match prompt_mode { - reedline::PromptEditMode::Default => std::borrow::Cow::Borrowed(">>"), - reedline::PromptEditMode::Emacs => { - let timestamp = Local::now().format("[%H:%M:%S.%3f/SHELL] >>\t").to_string(); - std::borrow::Cow::Owned(timestamp) - } - reedline::PromptEditMode::Vi(_) => std::borrow::Cow::Borrowed("vi>>"), - reedline::PromptEditMode::Custom(_) => std::borrow::Cow::Borrowed("custom>>"), - } - } - - fn render_prompt_multiline_indicator(&self) -> std::borrow::Cow { - std::borrow::Cow::Borrowed("><") - } -} fn evaluate_command(input: &str) { if input.trim().is_empty() { @@ -115,30 +79,35 @@ fn evaluate_command(input: &str) { } } -pub async fn handle_repl() { - let mut line_editor = Reedline::create(); +pub async fn handle_repl() -> rustyline::Result<()> { + let mut line_editor = DefaultEditor::new()?; + if line_editor.load_history("history.txt").is_err() { + debug!("No previous history."); + } + let time = Local::now().format("%H:%M:%S.%3f").to_string(); + let prompt = format!("[{}/{}] {}", time,"SHELL", ">>\t"); register_commands(); loop { - let sig = line_editor.read_line(&ZPrompt { - left_text: String::new(), - right_text: "<<".to_string(), - }); - + let sig = line_editor.readline( + &prompt.bright_white() + ); match sig { - Ok(Signal::Success(buffer)) => { - if buffer == "exit" { - std::process::exit(0); - } else { - evaluate_command(&buffer); - } + Ok(line) => { + line_editor.add_history_entry(line.as_str())?; + evaluate_command(line.as_str()); } - Ok(Signal::CtrlC) => { - println!("\nCONTROL+C RECEIVED, TERMINATING"); + Err(rustyline::error::ReadlineError::Interrupted) => { + println!("CTRL+C received, exiting..."); std::process::exit(0); } - err => { - eprintln!("Error: {:?}", err); + Err(rustyline::error::ReadlineError::Eof) => { + println!("Error: CTRL+D pressed. Exiting..."); + std::process::exit(0); + } + Err(err) => { + println!("Error: {}", err); + } } } diff --git a/engine/src/main.rs b/engine/src/main.rs index 5553944..089f508 100644 --- a/engine/src/main.rs +++ b/engine/src/main.rs @@ -24,24 +24,22 @@ async fn main() -> Result<()> { if cli.log { info!("Initializing Engine with logging to stdout enabled"); - warn!("REPL cannot be used with logging enabled due to ReedLine not supporting writing to stdout"); core::init_renderer()?; } else { LOGGER.write_to_stdout(); info!("Initializing Engine with logging to stdout disabled"); - warn!("REPL cannot be used with logging enabled due to ReedLine not supporting writing to stdout"); info!("Writing all logs to file z.log"); LOGGER.write_to_file("z.log"); info!("Logging back to file z.log"); let shell_thread = tokio::task::spawn(async { - core::repl::repl::handle_repl().await; + core::repl::repl::handle_repl().await }); core::init_renderer()?; - shell_thread.await?; + shell_thread.await??; // LOL - Caz } Ok(())