(&mut self)
| 53 | } |
| 54 | |
| 55 | pub fn run(&mut self) -> Result<(), VmError> { |
| 56 | println!("AI Script REPL v0.1.0"); |
| 57 | println!("Type '.help' for more information."); |
| 58 | |
| 59 | loop { |
| 60 | let prompt = if self.buffer.is_empty() { "> " } else { "... " }; |
| 61 | |
| 62 | // Read line with history support |
| 63 | match self.editor.readline(prompt) { |
| 64 | Ok(line) => { |
| 65 | let input = line.trim(); |
| 66 | |
| 67 | // Add valid commands to history |
| 68 | if !input.is_empty() && self.buffer.is_empty() { |
| 69 | self.editor.add_history_entry(line.as_str()).unwrap(); |
| 70 | self.editor |
| 71 | .save_history(&self.history_path) |
| 72 | .unwrap_or_else(|e| { |
| 73 | eprintln!("Error saving history: {}", e); |
| 74 | }); |
| 75 | } |
| 76 | |
| 77 | if input.is_empty() && !self.buffer.is_empty() { |
| 78 | // Empty line in multi-line mode - execute the buffered code |
| 79 | let code = self.buffer.clone(); |
| 80 | self.buffer.clear(); |
| 81 | self.brace_depth = 0; |
| 82 | self.execute_code(&code)?; |
| 83 | continue; |
| 84 | } |
| 85 | |
| 86 | // Handle special commands |
| 87 | match input { |
| 88 | ".help" => { |
| 89 | println!("Available commands:"); |
| 90 | println!(" .help Show this help message"); |
| 91 | println!(" .clear Clear the current buffer"); |
| 92 | println!(" .exit Exit the REPL"); |
| 93 | println!("\nUse arrow keys ↑/↓ to navigate history"); |
| 94 | continue; |
| 95 | } |
| 96 | ".clear" => { |
| 97 | self.buffer.clear(); |
| 98 | self.brace_depth = 0; |
| 99 | continue; |
| 100 | } |
| 101 | ".exit" => break, |
| 102 | _ => {} |
| 103 | } |
| 104 | |
| 105 | // Track brace depth for multi-line input |
| 106 | for c in input.chars() { |
| 107 | match c { |
| 108 | '{' => self.brace_depth += 1, |
| 109 | '}' => self.brace_depth -= 1, |
| 110 | _ => {} |
| 111 | } |
| 112 | } |
no test coverage detected