From 8725654a746fa8c999fbd5437559fdfcf1f7fb53 Mon Sep 17 00:00:00 2001 From: Denis Isidoro Date: Tue, 23 Nov 2021 09:54:25 -0300 Subject: [PATCH] Allow multi-word shell.command config (#644) Fixes #645 --- docs/config_file_example.yaml | 1 + src/config/env.rs | 2 -- src/config/mod.rs | 8 ++++++++ src/config/yaml.rs | 2 ++ src/env_var.rs | 2 -- src/finder/mod.rs | 2 +- src/shell.rs | 12 ++++++++---- tests/config.yaml | 18 ++++++++++++++++++ tests/helpers.sh | 5 +++++ tests/no_prompt_cheats/cases.cheat | 3 +++ tests/run | 2 +- 11 files changed, 47 insertions(+), 10 deletions(-) create mode 100644 tests/config.yaml create mode 100644 tests/helpers.sh diff --git a/docs/config_file_example.yaml b/docs/config_file_example.yaml index dcf904d5..d58a6664 100644 --- a/docs/config_file_example.yaml +++ b/docs/config_file_example.yaml @@ -29,3 +29,4 @@ finder: shell: command: bash # shell used for shell out. possible values: bash, zsh, dash, ... + # finder_command: bash # similar, but for fzf's internals diff --git a/src/config/env.rs b/src/config/env.rs index e2b364a7..cf1c017a 100644 --- a/src/config/env.rs +++ b/src/config/env.rs @@ -8,7 +8,6 @@ pub struct EnvConfig { pub config_yaml: Option, pub config_path: Option, pub path: Option, - pub shell: Option, pub finder: Option, pub fzf_overrides: Option, pub fzf_overrides_var: Option, @@ -20,7 +19,6 @@ impl EnvConfig { config_yaml: env_var::get(env_var::CONFIG_YAML).ok(), config_path: env_var::get(env_var::CONFIG).ok(), path: env_var::get(env_var::PATH).ok(), - shell: env_var::get(env_var::SHELL).ok(), finder: env_var::get(env_var::FINDER) .ok() .and_then(|x| FinderChoice::from_str(&x).ok()), diff --git a/src/config/mod.rs b/src/config/mod.rs index 30ed144c..cb977b1f 100644 --- a/src/config/mod.rs +++ b/src/config/mod.rs @@ -93,6 +93,14 @@ impl Config { self.yaml.shell.command.clone() } + pub fn finder_shell(&self) -> String { + self.yaml + .shell + .finder_command + .clone() + .unwrap_or_else(|| self.yaml.shell.command.clone()) + } + pub fn tag_rules(&self) -> Option { self.clap .tag_rules diff --git a/src/config/yaml.rs b/src/config/yaml.rs index 89519aa5..09e683ef 100644 --- a/src/config/yaml.rs +++ b/src/config/yaml.rs @@ -80,6 +80,7 @@ pub struct Search { #[serde(default)] pub struct Shell { pub command: String, + pub finder_command: Option, } #[derive(Deserialize, Default)] @@ -177,6 +178,7 @@ impl Default for Shell { fn default() -> Self { Self { command: "bash".to_string(), + finder_command: None, } } } diff --git a/src/env_var.rs b/src/env_var.rs index 2eb1dca2..6aea2a30 100644 --- a/src/env_var.rs +++ b/src/env_var.rs @@ -16,8 +16,6 @@ pub const FZF_OVERRIDES: &str = "NAVI_FZF_OVERRIDES"; pub const FZF_OVERRIDES_VAR: &str = "NAVI_FZF_OVERRIDES_VAR"; pub const FINDER: &str = "NAVI_FINDER"; -pub const SHELL: &str = "NAVI_SHELL"; - pub const CONFIG: &str = "NAVI_CONFIG"; pub const CONFIG_YAML: &str = "NAVI_CONFIG_YAML"; diff --git a/src/finder/mod.rs b/src/finder/mod.rs index a710a7d7..0285d020 100644 --- a/src/finder/mod.rs +++ b/src/finder/mod.rs @@ -160,7 +160,7 @@ impl Finder for FinderChoice { } let child = command - .env("SHELL", CONFIG.shell()) + .env("SHELL", CONFIG.finder_shell()) .stdin(Stdio::piped()) .stdout(Stdio::piped()) .spawn(); diff --git a/src/shell.rs b/src/shell.rs index b894d514..d65d2288 100644 --- a/src/shell.rs +++ b/src/shell.rs @@ -36,10 +36,14 @@ impl ShellSpawnError { } pub fn out() -> Command { - let shell = CONFIG.shell(); - let mut cmd = Command::new(&shell); - let arg = if shell == "cmd.exe" { "/c" } else { "-c" }; - cmd.arg(arg); + let words_str = CONFIG.shell(); + let mut words_vec = shellwords::split(&words_str).expect("empty shell command"); + let mut words = words_vec.iter_mut(); + let first_cmd = words.next().expect("absent shell binary"); + let mut cmd = Command::new(&first_cmd); + cmd.args(words); + let dash_c = if words_str.contains("cmd.exe") { "/c" } else { "-c" }; + cmd.arg(dash_c); cmd } diff --git a/tests/config.yaml b/tests/config.yaml new file mode 100644 index 00000000..40306478 --- /dev/null +++ b/tests/config.yaml @@ -0,0 +1,18 @@ +style: + tag: + color: cyan + width_percentage: 26 + min_width: 20 + comment: + color: yellow + width_percentage: 42 + min_width: 45 + snippet: + color: white + +finder: + command: fzf + +shell: + finder_command: bash + command: env BASH_ENV="${NAVI_HOME}/tests/helpers.sh" bash --norc --noprofile diff --git a/tests/helpers.sh b/tests/helpers.sh new file mode 100644 index 00000000..533bba5e --- /dev/null +++ b/tests/helpers.sh @@ -0,0 +1,5 @@ +#!/usr/local/bin/env bash + +myhelperfn() { + echo "inside helper: $*" +} diff --git a/tests/no_prompt_cheats/cases.cheat b/tests/no_prompt_cheats/cases.cheat index 653ba2a1..8367d49d 100644 --- a/tests/no_prompt_cheats/cases.cheat +++ b/tests/no_prompt_cheats/cases.cheat @@ -61,6 +61,9 @@ echo "foo" \ # multiline variable -> "foo bar" echo "" +# helper -> "inside helper: 42" +myhelperfn 42 + $ x: echo '2' $ x2: echo "$((x+10))" $ y: echo 'a' diff --git a/tests/run b/tests/run index 25cf33b7..08e90946 100755 --- a/tests/run +++ b/tests/run @@ -19,7 +19,7 @@ _navi() { local path="${NAVI_TEST_PATH:-$TEST_CHEAT_PATH}" path="${path//$HOME/~}" export NAVI_ENV_VAR_PATH="$path" - RUST_BACKTRACE=1 NAVI_PATH='$NAVI_ENV_VAR_PATH' "$NAVI_EXE" "$@" + RUST_BACKTRACE=1 NAVI_PATH='$NAVI_ENV_VAR_PATH' NAVI_CONFIG="${NAVI_HOME}/tests/config.yaml" "$NAVI_EXE" "$@" } _navi_cases() {