diff --git a/docs/src/worktrees.md b/docs/src/worktrees.md index 7dd4799..baa1f4b 100644 --- a/docs/src/worktrees.md +++ b/docs/src/worktrees.md @@ -259,6 +259,9 @@ persistent_branches = [ ] ``` +Note that setting persistent branches will disable any detection of "default" +branches. The first entry will be considered your repositories' default branch. + ### Converting an existing repository It is possible to convert an existing directory to a worktree setup, using `grm diff --git a/e2e_tests/test_worktree_clean.py b/e2e_tests/test_worktree_clean.py index fa916e1..17f16ce 100644 --- a/e2e_tests/test_worktree_clean.py +++ b/e2e_tests/test_worktree_clean.py @@ -1,5 +1,7 @@ #!/usr/bin/env python3 +import pytest + from helpers import * @@ -139,3 +141,56 @@ def test_worktree_clean_non_git(): assert cmd.returncode != 0 assert len(cmd.stdout) == 0 assert len(cmd.stderr) != 0 + + +@pytest.mark.parametrize("configure_default_branch", [True, False]) +@pytest.mark.parametrize("branch_list_empty", [True, False]) +def test_worktree_clean_configured_default_branch( + configure_default_branch, branch_list_empty +): + with TempGitRepositoryWorktree() as (base_dir, _commit): + if configure_default_branch: + with open(os.path.join(base_dir, "grm.toml"), "w") as f: + if branch_list_empty: + f.write( + f""" + persistent_branches = [] + """ + ) + else: + f.write( + f""" + persistent_branches = [ + "mybranch" + ] + """ + ) + + cmd = grm(["wt", "add", "test"], cwd=base_dir) + assert cmd.returncode == 0 + + shell( + f""" + cd {base_dir} + ( + cd ./test + touch change + git add change + git commit -m commit + ) + + git --git-dir ./.git-main-working-tree worktree add mybranch + ( + cd ./mybranch + git merge --no-ff test + ) + git --git-dir ./.git-main-working-tree worktree remove mybranch + """ + ) + + cmd = grm(["wt", "clean"], cwd=base_dir) + assert cmd.returncode == 0 + if configure_default_branch and not branch_list_empty: + assert "test" not in os.listdir(base_dir) + else: + assert "test" in os.listdir(base_dir) diff --git a/src/repo.rs b/src/repo.rs index b60eb5e..2daba33 100644 --- a/src/repo.rs +++ b/src/repo.rs @@ -880,16 +880,29 @@ impl Repo { .get_worktrees() .map_err(|error| format!("Getting worktrees failed: {}", error))?; - let default_branch = self - .default_branch() - .map_err(|error| format!("Failed getting default branch: {}", error))?; - - let default_branch_name = default_branch - .name() - .map_err(|error| format!("Failed getting default branch name: {}", error))?; - let config = read_worktree_root_config(directory)?; + let guess_default_branch = || { + self.default_branch() + .map_err(|_| "Could not determine default branch")? + .name() + .map_err(|error| format!("Failed getting default branch name: {}", error)) + }; + + let default_branch_name = match &config { + None => guess_default_branch()?, + Some(config) => match &config.persistent_branches { + None => guess_default_branch()?, + Some(persistent_branches) => { + if persistent_branches.is_empty() { + guess_default_branch()? + } else { + persistent_branches[0].clone() + } + } + }, + }; + for worktree in worktrees .iter() .filter(|worktree| *worktree != &default_branch_name) @@ -946,13 +959,28 @@ impl Repo { .unwrap(), ); - let default_branch = self - .default_branch() - .map_err(|error| format!("Failed getting default branch: {}", error))?; + let config = read_worktree_root_config(directory)?; - let default_branch_name = default_branch - .name() - .map_err(|error| format!("Failed getting default branch name: {}", error))?; + let guess_default_branch = || { + self.default_branch() + .map_err(|error| format!("Failed getting default branch: {}", error))? + .name() + .map_err(|error| format!("Failed getting default branch name: {}", error)) + }; + + let default_branch_name = match &config { + None => guess_default_branch()?, + Some(config) => match &config.persistent_branches { + None => guess_default_branch()?, + Some(persistent_branches) => { + if persistent_branches.is_empty() { + guess_default_branch()? + } else { + persistent_branches[0].clone() + } + } + }, + }; if dirname == crate::GIT_MAIN_WORKTREE_DIRECTORY { continue;