diff options
author | Blaž Hrastnik | 2021-06-01 05:47:21 +0000 |
---|---|---|
committer | Blaž Hrastnik | 2021-06-01 08:26:03 +0000 |
commit | ce25aa951e4bd4352fc211258014557e69cc5c5c (patch) | |
tree | 7c8d34c6ee95f4f4041c6774c3590ccda6bace3c /helix-view | |
parent | a2147fc7d56f9f5cb614d8c80b154a545dd59f00 (diff) |
Allow setting a filepath on :write
Diffstat (limited to 'helix-view')
-rw-r--r-- | helix-view/src/document.rs | 52 |
1 files changed, 51 insertions, 1 deletions
diff --git a/helix-view/src/document.rs b/helix-view/src/document.rs index 7d912ec0..51d8a795 100644 --- a/helix-view/src/document.rs +++ b/helix-view/src/document.rs @@ -1,6 +1,6 @@ use anyhow::{Context, Error}; use std::future::Future; -use std::path::{Path, PathBuf}; +use std::path::{Component, Path, PathBuf}; use std::sync::Arc; use helix_core::{ @@ -64,6 +64,42 @@ where } } +/// Normalize a path, removing things like `.` and `..`. +/// +/// CAUTION: This does not resolve symlinks (unlike +/// [`std::fs::canonicalize`]). This may cause incorrect or surprising +/// behavior at times. This should be used carefully. Unfortunately, +/// [`std::fs::canonicalize`] can be hard to use correctly, since it can often +/// fail, or on Windows returns annoying device paths. This is a problem Cargo +/// needs to improve on. +/// Copied from cargo: https://github.com/rust-lang/cargo/blob/070e459c2d8b79c5b2ac5218064e7603329c92ae/crates/cargo-util/src/paths.rs#L81 +pub fn normalize_path(path: &Path) -> PathBuf { + let mut components = path.components().peekable(); + let mut ret = if let Some(c @ Component::Prefix(..)) = components.peek().cloned() { + components.next(); + PathBuf::from(c.as_os_str()) + } else { + PathBuf::new() + }; + + for component in components { + match component { + Component::Prefix(..) => unreachable!(), + Component::RootDir => { + ret.push(component.as_os_str()); + } + Component::CurDir => {} + Component::ParentDir => { + ret.pop(); + } + Component::Normal(c) => { + ret.push(c); + } + } + } + ret +} + use helix_lsp::lsp; use url::Url; @@ -176,6 +212,20 @@ impl Document { } } + pub fn set_path(&mut self, path: &Path) -> Result<(), std::io::Error> { + // canonicalize path to absolute value + let current_dir = std::env::current_dir()?; + let path = normalize_path(¤t_dir.join(path)); + + if let Some(parent) = path.parent() { + // TODO: return error as necessary + if parent.exists() { + self.path = Some(path); + } + } + Ok(()) + } + pub fn set_language( &mut self, language_config: Option<Arc<helix_core::syntax::LanguageConfiguration>>, |