Skip to content

Commit

Permalink
adapt to changes in gix-dir
Browse files Browse the repository at this point in the history
This includes an improvement on how `gix` initiates a dirwalk with the purpose
of deletion so that worktrees are protected should the fall into the parent-repository
working directory.
  • Loading branch information
Byron committed Jul 25, 2024
1 parent c9cd2d2 commit 37c2852
Show file tree
Hide file tree
Showing 5 changed files with 35 additions and 5 deletions.
2 changes: 1 addition & 1 deletion gix-status/src/index_as_worktree_with_renames/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ pub(super) mod function {
objects: Find,
progress: &mut dyn gix_features::progress::Progress,
mut ctx: Context<'_>,
options: Options,
options: Options<'_>,
) -> Result<Outcome, Error>
where
T: Send + Clone,
Expand Down
4 changes: 2 additions & 2 deletions gix-status/src/index_as_worktree_with_renames/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -274,7 +274,7 @@ impl<ContentChange, SubmoduleStatus> Entry<'_, ContentChange, SubmoduleStatus> {

/// Options for use in [index_as_worktree_with_renames()](crate::index_as_worktree_with_renames()).
#[derive(Clone, Default)]
pub struct Options {
pub struct Options<'a> {
/// The way all output should be sorted.
///
/// If `None`, and depending on the `rewrites` field, output will be immediate but the output order
Expand All @@ -299,7 +299,7 @@ pub struct Options {
///
/// If `None`, the directory walk portion will not run at all, yielding data similar
/// to a bare [index_as_worktree()](crate::index_as_worktree()) call.
pub dirwalk: Option<gix_dir::walk::Options>,
pub dirwalk: Option<gix_dir::walk::Options<'a>>,
/// The configuration for the rewrite tracking. Note that if set, the [`dirwalk`](Self::dirwalk) should be configured
/// to *not* collapse untracked and ignored entries, as rewrite tracking is on a file-by-file basis.
/// Also note that when `Some(_)`, it will collect certain changes depending on the exact configuration, which typically increases
Expand Down
2 changes: 2 additions & 0 deletions gix/src/dirwalk/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@ pub enum Error {
Prefix(#[from] gix_path::realpath::Error),
#[error(transparent)]
FilesystemOptions(#[from] config::boolean::Error),
#[error("Could not list worktrees to assure they are no candidates for deletion")]
ListWorktrees(#[from] std::io::Error),
}

/// The outcome of the [dirwalk()](crate::Repository::dirwalk).
Expand Down
3 changes: 2 additions & 1 deletion gix/src/dirwalk/options.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ impl Options {
}
}

impl From<Options> for gix_dir::walk::Options {
impl From<Options> for gix_dir::walk::Options<'static> {
fn from(v: Options) -> Self {
gix_dir::walk::Options {
precompose_unicode: v.precompose_unicode,
Expand All @@ -38,6 +38,7 @@ impl From<Options> for gix_dir::walk::Options {
emit_collapsed: v.emit_collapsed,
symlinks_to_directories_are_ignored_like_directories: v
.symlinks_to_directories_are_ignored_like_directories,
worktree_relative_worktree_dirs: None,
}
}
}
Expand Down
29 changes: 28 additions & 1 deletion gix/src/repository/dirwalk.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,12 @@ impl Repository {
/// lookup. Note that items will only count as tracked if they have the [`gix_index::entry::Flags::UPTODATE`]
/// flag set.
///
/// Note that dirwalks for the purpose of deletion will be initialized with the worktrees of this repository
/// if they fall into the working directory of this repository as well to mark them as `tracked`. That way
/// it's hard to accidentally flag them for deletion.
/// This is intentionally not the case when deletion is not intended so they look like
/// untracked repositories instead.
///
/// See [`gix_dir::walk::delegate::Collect`] for a delegate that collects all seen entries.
pub fn dirwalk(
&self,
Expand Down Expand Up @@ -48,6 +54,27 @@ impl Repository {
crate::path::realpath_opts(self.git_dir(), self.current_dir(), crate::path::realpath::MAX_SYMLINKS)?;
let fs_caps = self.filesystem_options()?;
let accelerate_lookup = fs_caps.ignore_case.then(|| index.prepare_icase_backing());
let mut opts = gix_dir::walk::Options::from(options);
let worktree_relative_worktree_dirs_storage;
if let Some(workdir) = self.work_dir().filter(|_| opts.for_deletion.is_some()) {
let linked_worktrees = self.worktrees()?;
if !linked_worktrees.is_empty() {
let real_workdir = gix_path::realpath_opts(
workdir,
self.options.current_dir_or_empty(),
gix_path::realpath::MAX_SYMLINKS,
)?;
worktree_relative_worktree_dirs_storage = linked_worktrees
.into_iter()
.filter_map(|proxy| proxy.base().ok())
.filter_map(|base| base.strip_prefix(&real_workdir).map(ToOwned::to_owned).ok())
.map(|rela_path| {
gix_path::to_unix_separators_on_windows(gix_path::into_bstr(rela_path)).into_owned()
})
.collect();
opts.worktree_relative_worktree_dirs = Some(&worktree_relative_worktree_dirs_storage);
}
}
let (outcome, traversal_root) = gix_dir::walk(
workdir,
gix_dir::walk::Context {
Expand All @@ -71,7 +98,7 @@ impl Repository {
objects: &self.objects,
explicit_traversal_root: (!options.empty_patterns_match_prefix).then_some(workdir),
},
options.into(),
opts,
delegate,
)?;

Expand Down

0 comments on commit 37c2852

Please sign in to comment.