diff options
author | Dan Davison <dandavison7@gmail.com> | 2022-01-06 18:33:36 -0500 |
---|---|---|
committer | Dan Davison <dandavison7@gmail.com> | 2022-01-17 18:30:32 -0500 |
commit | e9e9fb7c6975ae9f0a04cf4f14fec4a38c281af1 (patch) | |
tree | 71d2dff2ce102caac56c91dc1311b73241b9b11a | |
parent | fb38eddd9a8b6faa079ff8bdac2affc3b7c3f2b3 (diff) |
Construct hyperlink file path relative to cwd
Fixes #890
-rw-r--r-- | src/config.rs | 2 | ||||
-rw-r--r-- | src/features/hyperlinks.rs | 6 | ||||
-rw-r--r-- | src/git_config/git_config_entry.rs | 2 | ||||
-rw-r--r-- | src/handlers/hunk_header.rs | 8 | ||||
-rw-r--r-- | src/options/set.rs | 9 | ||||
-rw-r--r-- | src/utils/cwd.rs | 25 | ||||
-rw-r--r-- | src/utils/mod.rs | 1 |
7 files changed, 33 insertions, 20 deletions
diff --git a/src/config.rs b/src/config.rs index 75bc7488..72fd4710 100644 --- a/src/config.rs +++ b/src/config.rs @@ -70,6 +70,7 @@ pub struct Config { pub color_only: bool, pub commit_regex: Regex, pub commit_style: Style, + pub cwd: Option<PathBuf>, pub cwd_relative_to_repo_root: Option<String>, pub decorations_width: cli::Width, pub default_language: Option<String>, @@ -254,6 +255,7 @@ impl From<cli::Opt> for Config { commit_style: styles["commit-style"], color_only: opt.color_only, commit_regex, + cwd: std::env::current_dir().ok(), cwd_relative_to_repo_root: std::env::var("GIT_PREFIX").ok(), decorations_width: opt.computed.decorations_width, default_language: opt.default_language, diff --git a/src/features/hyperlinks.rs b/src/features/hyperlinks.rs index ef85211e..4a2fb8fc 100644 --- a/src/features/hyperlinks.rs +++ b/src/features/hyperlinks.rs @@ -7,6 +7,7 @@ use regex::{Captures, Regex}; use crate::config::Config; use crate::features::OptionValueFunction; use crate::git_config::{GitConfig, GitConfigEntry, GitRemoteRepo}; +use crate::utils::cwd::cwd_of_user_shell_process; pub fn make_feature() -> Vec<(String, OptionValueFunction)> { builtin_feature!([ @@ -60,9 +61,8 @@ pub fn format_osc8_file_hyperlink<'a>( text: &str, config: &Config, ) -> Cow<'a, str> { - if let Some(GitConfigEntry::Path(workdir)) = config.git_config_entries.get("delta.__workdir__") - { - let absolute_path = workdir.join(relative_path); + if let Some(cwd) = cwd_of_user_shell_process(config) { + let absolute_path = cwd.join(relative_path); let mut url = config .hyperlinks_file_link_format .replace("{path}", &absolute_path.to_string_lossy()); diff --git a/src/git_config/git_config_entry.rs b/src/git_config/git_config_entry.rs index 81787181..2f026cf2 100644 --- a/src/git_config/git_config_entry.rs +++ b/src/git_config/git_config_entry.rs @@ -1,4 +1,3 @@ -use std::path::PathBuf; use std::result::Result; use std::str::FromStr; @@ -11,7 +10,6 @@ use crate::errors::*; pub enum GitConfigEntry { Style(String), GitRemote(GitRemoteRepo), - Path(PathBuf), } #[derive(Clone, Debug, PartialEq)] diff --git a/src/handlers/hunk_header.rs b/src/handlers/hunk_header.rs index f1d90900..32d0bea5 100644 --- a/src/handlers/hunk_header.rs +++ b/src/handlers/hunk_header.rs @@ -316,7 +316,6 @@ fn write_to_output_buffer( pub mod tests { use super::*; use crate::ansi::strip_ansi_codes; - use crate::git_config::GitConfigEntry; use crate::tests::integration_test_utils; #[test] @@ -410,14 +409,11 @@ pub mod tests { // returns a hyperlinked file path with line number. let mut cfg = integration_test_utils::make_config_from_args(&["--features", "hyperlinks"]); - cfg.git_config_entries.insert( - "delta.__workdir__".to_string(), - GitConfigEntry::Path("/some/workdir".into()), - ); + cfg.cwd = Some("/some/current/directory".into()); let result = paint_file_path_with_line_number(Some(3), "some-file", &cfg); - assert_eq!(result, "\u{1b}]8;;file:///some/workdir/some-file\u{1b}\\\u{1b}[34m3\u{1b}[0m\u{1b}]8;;\u{1b}\\"); + assert_eq!(result, "\u{1b}]8;;file:///some/current/directory/some-file\u{1b}\\\u{1b}[34m3\u{1b}[0m\u{1b}]8;;\u{1b}\\"); } #[test] diff --git a/src/options/set.rs b/src/options/set.rs index e82b9f39..f4806c1b 100644 --- a/src/options/set.rs +++ b/src/options/set.rs @@ -668,15 +668,6 @@ fn set_git_config_entries(opt: &mut cli::Opt, git_config: &mut GitConfig) { .insert(key.to_string(), GitConfigEntry::Style(style_string)); } } - - if let Some(repo) = &git_config.repo { - if let Some(workdir) = repo.workdir() { - opt.git_config_entries.insert( - "delta.__workdir__".to_string(), - GitConfigEntry::Path(workdir.to_path_buf()), - ); - } - } } #[cfg(test)] diff --git a/src/utils/cwd.rs b/src/utils/cwd.rs new file mode 100644 index 00000000..951c2ead --- /dev/null +++ b/src/utils/cwd.rs @@ -0,0 +1,25 @@ +use std::path::PathBuf; + +use crate::config::Config; + +/// Return current working directory of the user's shell process. I.e. the directory in which they +/// are in when delta exits. This is the directory relative to which the file paths in delta output +/// are constructed if they are using either (a) delta's relative-paths option or (b) git's +/// --relative flag. +pub fn cwd_of_user_shell_process(config: &Config) -> Option<PathBuf> { + match (&config.cwd, &config.cwd_relative_to_repo_root) { + (Some(cwd), None) => { + // We are not a child process of git + Some(PathBuf::from(cwd)) + } + (Some(repo_root), Some(cwd_relative_to_repo_root)) => { + // We are a child process of git; git spawned us from repo_root and preserved the user's + // original cwd in the GIT_PREFIX env var (available as config.cwd_relative_to_repo_root) + Some(PathBuf::from(repo_root).join(cwd_relative_to_repo_root)) + } + (None, _) => { + // Unexpected + None + } + } +} diff --git a/src/utils/mod.rs b/src/utils/mod.rs index 46ea9906..63089531 100644 --- a/src/utils/mod.rs +++ b/src/utils/mod.rs @@ -1,5 +1,6 @@ #[cfg(not(tarpaulin_include))] pub mod bat; +pub mod cwd; pub mod process; pub mod regex_replacement; pub mod syntect; |