Mercurial > public > mercurial-scm > hg
view rust/hg-core/src/operations/find_root.rs @ 46154:ecbb2fc9418c
copies-rust: rename Oracle.is_ancestor to Oracle.is_overwrite
The core information that we want here is about "does information from revision
X overwrite information in Y". To do so, we check is X is an ancestors of Y, but
this is an implementation details, they could be other ways. We update the
naming to clarify this (and align more with wording used in upcoming changesets.
For people curious about other ways: for example we could record the overwrite
graph as it happens and reuse that to check if X overwrite Y, without having to
do potential expensive `is_ancestor` call on the revision graph.
Differential Revision: https://phab.mercurial-scm.org/D9496
author | Pierre-Yves David <pierre-yves.david@octobus.net> |
---|---|
date | Wed, 02 Dec 2020 16:11:35 +0100 |
parents | dca9cb99971c |
children | 3e2d539d0d1a |
line wrap: on
line source
use std::fmt; use std::path::{Path, PathBuf}; /// Kind of error encoutered by FindRoot #[derive(Debug)] pub enum FindRootErrorKind { /// Root of the repository has not been found /// Contains the current directory used by FindRoot RootNotFound(PathBuf), /// The current directory does not exists or permissions are insufficient /// to get access to it GetCurrentDirError(std::io::Error), } /// A FindRoot error #[derive(Debug)] pub struct FindRootError { /// Kind of error encoutered by FindRoot pub kind: FindRootErrorKind, } impl std::error::Error for FindRootError {} impl fmt::Display for FindRootError { fn fmt(&self, _f: &mut fmt::Formatter<'_>) -> fmt::Result { unimplemented!() } } /// Find the root of the repository /// by searching for a .hg directory in the process’ current directory and its /// ancestors pub fn find_root() -> Result<PathBuf, FindRootError> { let current_dir = std::env::current_dir().map_err(|e| FindRootError { kind: FindRootErrorKind::GetCurrentDirError(e), })?; Ok(find_root_from_path(¤t_dir)?.into()) } /// Find the root of the repository /// by searching for a .hg directory in the given directory and its ancestors pub fn find_root_from_path(start: &Path) -> Result<&Path, FindRootError> { if start.join(".hg").exists() { return Ok(start); } for ancestor in start.ancestors() { if ancestor.join(".hg").exists() { return Ok(ancestor); } } Err(FindRootError { kind: FindRootErrorKind::RootNotFound(start.into()), }) } #[cfg(test)] mod tests { use super::*; use std::fs; use tempfile; #[test] fn dot_hg_not_found() { let tmp_dir = tempfile::tempdir().unwrap(); let path = tmp_dir.path(); let err = find_root_from_path(&path).unwrap_err(); // TODO do something better assert!(match err { FindRootError { kind } => match kind { FindRootErrorKind::RootNotFound(p) => p == path.to_path_buf(), _ => false, }, }) } #[test] fn dot_hg_in_current_path() { let tmp_dir = tempfile::tempdir().unwrap(); let root = tmp_dir.path(); fs::create_dir_all(root.join(".hg")).unwrap(); let result = find_root_from_path(&root).unwrap(); assert_eq!(result, root) } #[test] fn dot_hg_in_parent() { let tmp_dir = tempfile::tempdir().unwrap(); let root = tmp_dir.path(); fs::create_dir_all(root.join(".hg")).unwrap(); let directory = root.join("some/nested/directory"); let result = find_root_from_path(&directory).unwrap(); assert_eq!(result, root) } } /* tests */