From 14debc811436de28533f2126556996c3e3b0f542 Mon Sep 17 00:00:00 2001 From: Jeff Dickey <216188+jdx@users.noreply.github.com> Date: Fri, 26 Jan 2024 17:43:35 -0600 Subject: [PATCH] added `env._.source` feature --- e2e/test_env_source | 20 ++++++++++++++++++++ man/man1/mise.1 | 4 ++-- src/config/env_directive.rs | 24 ++++++++++++++++++++++-- 3 files changed, 44 insertions(+), 4 deletions(-) create mode 100755 e2e/test_env_source diff --git a/e2e/test_env_source b/e2e/test_env_source new file mode 100755 index 0000000000..085516dcf5 --- /dev/null +++ b/e2e/test_env_source @@ -0,0 +1,20 @@ +#!/usr/bin/env bash +set -euo pipefail +# shellcheck source-path=SCRIPTDIR +source "$(dirname "$0")/assert.sh" + +export MISE_EXPERIMENTAL=1 + +mkdir -p "$(dirname "$MISE_GLOBAL_CONFIG_FILE")" "$MISE_CONFIG_DIR" + +cat >"$MISE_GLOBAL_CONFIG_FILE" <"$MISE_CONFIG_DIR/source.sh" < diff --git a/src/config/env_directive.rs b/src/config/env_directive.rs index 1baa88b540..2b3908d7f3 100644 --- a/src/config/env_directive.rs +++ b/src/config/env_directive.rs @@ -1,5 +1,7 @@ use crate::config::config_file::trust_check; +use crate::config::Settings; use crate::dirs; +use crate::env_diff::{EnvDiff, EnvDiffOperation}; use crate::file::display_path; use crate::tera::{get_tera, BASE_CONTEXT}; use eyre::Context; @@ -60,6 +62,7 @@ impl EnvResults { initial: &HashMap, input: Vec<(EnvDirective, PathBuf)>, ) -> eyre::Result { + let settings = Settings::get(); let mut ctx = BASE_CONTEXT.clone(); let mut env = initial .iter() @@ -75,7 +78,11 @@ impl EnvResults { for (directive, source) in input { let config_root = source.parent().unwrap(); ctx.insert("config_root", config_root); - ctx.insert("env", &env); + let env_vars = env + .iter() + .map(|(k, (v, _))| (k.clone(), v.clone())) + .collect::>(); + ctx.insert("env", &env_vars); let normalize_path = |s: String| { let s = s.strip_prefix("./").unwrap_or(&s); match s.strip_prefix("~/") { @@ -112,11 +119,24 @@ impl EnvResults { } } EnvDirective::Source(input) => { + settings.ensure_experimental()?; trust_check(&source)?; let s = r.parse_template(&ctx, &source, input.to_string_lossy().as_ref())?; let p = normalize_path(s); r.env_scripts.push(p.clone()); - // TODO: run script and apply diff + let env_diff = EnvDiff::from_bash_script(&p, env_vars.clone())?; + for p in env_diff.to_patches() { + match p { + EnvDiffOperation::Add(k, v) | EnvDiffOperation::Change(k, v) => { + r.env_remove.remove(&k); + env.insert(k.clone(), (v.clone(), Some(source.clone()))); + } + EnvDiffOperation::Remove(k) => { + env.remove(&k); + r.env_remove.insert(k); + } + } + } } }; }