From ee563ecf4e92a77383aca335662300c555639b2d Mon Sep 17 00:00:00 2001 From: Fernando Herrera Date: Sat, 14 Aug 2021 19:14:14 +0100 Subject: [PATCH] PROMPT_STRING env variable (#3918) * prompt string env variable * cargo clippy --- crates/nu-cli/src/cli.rs | 139 +++++++++++++++++++++------------------ 1 file changed, 74 insertions(+), 65 deletions(-) diff --git a/crates/nu-cli/src/cli.rs b/crates/nu-cli/src/cli.rs index ac8ebf4912..a2c1847316 100644 --- a/crates/nu-cli/src/cli.rs +++ b/crates/nu-cli/src/cli.rs @@ -31,9 +31,12 @@ use std::error::Error; use std::iter::Iterator; use std::path::PathBuf; +// Name of environment variable where the prompt could be stored +#[cfg(feature = "rustyline-support")] +const PROMPT_STRING: &str = "PROMPT_STRING"; + pub fn search_paths() -> Vec { use std::env; - let mut search_paths = Vec::new(); // Automatically add path `nu` is in as a search path @@ -83,6 +86,66 @@ pub fn run_script_file( Ok(()) } +#[cfg(feature = "rustyline-support")] +fn default_prompt_string(cwd: &str) -> String { + format!( + "{}{}{}{}{}{}> ", + Color::Green.bold().prefix().to_string(), + cwd, + nu_ansi_term::ansi::RESET, + Color::Cyan.bold().prefix().to_string(), + current_branch(), + nu_ansi_term::ansi::RESET + ) +} + +#[cfg(feature = "rustyline-support")] +fn evaluate_prompt_string(prompt_line: &str, context: &EvaluationContext, cwd: &str) -> String { + context.scope.enter_scope(); + let (prompt_block, err) = nu_parser::parse(prompt_line, 0, &context.scope); + + if err.is_some() { + context.scope.exit_scope(); + default_prompt_string(cwd) + } else { + let run_result = run_block( + &prompt_block, + context, + InputStream::empty(), + ExternalRedirection::Stdout, + ); + context.scope.exit_scope(); + + match run_result { + Ok(result) => match result.collect_string(Tag::unknown()) { + Ok(string_result) => { + let errors = context.get_errors(); + maybe_print_errors(context, Text::from(prompt_line)); + context.clear_errors(); + + if !errors.is_empty() { + "> ".into() + } else { + string_result.item + } + } + Err(e) => { + context.host().lock().print_err(e, &Text::from(prompt_line)); + context.clear_errors(); + + "> ".into() + } + }, + Err(e) => { + context.host().lock().print_err(e, &Text::from(prompt_line)); + context.clear_errors(); + + "> ".into() + } + } + } +} + #[cfg(feature = "rustyline-support")] pub fn cli( context: EvaluationContext, @@ -235,72 +298,17 @@ pub fn cli( let cwd = context.shell_manager().path(); - let colored_prompt = { - if let Some(prompt) = &prompt { - let prompt_line = prompt.as_string()?; - - context.scope.enter_scope(); - let (prompt_block, err) = nu_parser::parse(&prompt_line, 0, &context.scope); - - if err.is_some() { - context.scope.exit_scope(); - - format!( - "{}{}{}{}{}{}> ", - Color::Green.bold().prefix().to_string(), - cwd, - nu_ansi_term::ansi::RESET, - Color::Cyan.bold().prefix().to_string(), - current_branch(), - nu_ansi_term::ansi::RESET - ) + // Check if the PROMPT_STRING env variable is set. This env variable + // contains nu code that is used to overwrite the prompt + let colored_prompt = match context.scope.get_env(PROMPT_STRING) { + Some(env_prompt) => evaluate_prompt_string(&env_prompt, &context, &cwd), + None => { + if let Some(prompt) = &prompt { + let prompt_line = prompt.as_string()?; + evaluate_prompt_string(&prompt_line, &context, &cwd) } else { - let run_result = run_block( - &prompt_block, - &context, - InputStream::empty(), - ExternalRedirection::Stdout, - ); - context.scope.exit_scope(); - - match run_result { - Ok(result) => match result.collect_string(Tag::unknown()) { - Ok(string_result) => { - let errors = context.get_errors(); - maybe_print_errors(&context, Text::from(prompt_line)); - context.clear_errors(); - - if !errors.is_empty() { - "> ".to_string() - } else { - string_result.item - } - } - Err(e) => { - context.host().lock().print_err(e, &Text::from(prompt_line)); - context.clear_errors(); - - "> ".to_string() - } - }, - Err(e) => { - context.host().lock().print_err(e, &Text::from(prompt_line)); - context.clear_errors(); - - "> ".to_string() - } - } + default_prompt_string(&cwd) } - } else { - format!( - "{}{}{}{}{}{}> ", - Color::Green.bold().prefix().to_string(), - cwd, - nu_ansi_term::ansi::RESET, - Color::Cyan.bold().prefix().to_string(), - current_branch(), - nu_ansi_term::ansi::RESET - ) } }; @@ -432,6 +440,7 @@ pub fn cli( Ok(()) } +#[cfg(feature = "rustyline-support")] pub fn load_local_cfg_if_present(context: &EvaluationContext) { trace!("Loading local cfg if present"); match config::loadable_cfg_exists_in_dir(PathBuf::from(context.shell_manager().path())) {