gitbutlerapp/gitbutler · error
Cannot rename to ' ': a branch with that name already exists
Error message
Cannot rename to '{}': a branch with that name already exists What it means
Guard in legacy branch metadata rename: the new name already exists as a head in managed ref metadata, so renaming would produce duplicate refs/heads/<name> heads, which the rest of the code assumes never happens. Raised by rename when the caller picks a colliding target name; choose a unique branch name or delete the existing branch first.
Solutions
- Pick a different, unused name for the branch
- List existing branches and choose a unique name
- Delete or rename the conflicting branch first if it is no longer needed
Example fix
// before stack.rename(old, "feature-x") // feature-x already exists // after stack.rename(old, "feature-x-v2")
Defensive patterns
Strategy: validation
Validate before calling
// before renaming, check target uniqueness
if (stack.heads.some(b => fullName(b.name) === newFullName)) {
throw new Error(`Branch ${newName} already exists`);
} Try / catch
// Rust
match stack.rename(old, new_name) {
Err(e) if e.to_string().contains("already exists") => {
// prompt user for a different name
}
other => other,
} Prevention
- List existing branch names before choosing a rename target
- Use UI autocompletion to detect name collisions
- Avoid case-variant duplicates of existing names
When it happens
Trigger: Calling rename with a new_ref_name that matches (after full-name normalization) any existing branch head in the stack.
Common situations: Renaming a branch to a name that already exists in the workspace, case-variant duplicates, or reusing a recently deleted-but-recreated name.
Related errors
- Branch ' ' already exists
- Can only rename local branches under refs/heads, got
- Branch ' ' not found
- Branch ' ' not found when checking for conflicts
- Branch ' ' cannot be created: the target commit ( ) already…
AI-assisted analysis of gitbutlerapp/gitbutler@58e5313667 (2026-09-18).
Data as JSON: /api/errors/4bec95d349170418.
Report an issue: GitHub.
Appendix: source
Thrown at crates/but-meta/src/legacy/mod.rs:755
})
})
})
else {
// No managed metadata for this ref (e.g. an ad-hoc branch); nothing to rename here.
return Ok(());
};
// Refuse to rename onto a name that already exists in managed metadata: it would create
// duplicate `refs/heads/<name>` heads, which the rest of the code treats as an invariant
// violation (see the "There shouldn't be duplication" note in `branch()`).
let new_exists = self.data().branches.values().any(|stack| {
stack.heads.iter().any(|branch| {
full_branch_name(branch.name.as_str())
.is_some_and(|full_name| full_name.as_ref() == new_ref_name)
})
});
if new_exists {
bail!(
"Cannot rename to '{}': a branch with that name already exists",
new_ref_name.shorten()
);
}
let new_short_name = new_ref_name.shorten().to_string();
let stack = self
.data_mut()
.branches
.get_mut(&stack_id)
.expect("stack was just found");
stack.heads[branch_idx].name = new_short_name;
self.snapshot.set_changed_to_necessitate_write();
Ok(())
}
}
/// Ref metadata backed by legacy TOML for historical workspace metadata and byView on GitHub (pinned to 58e5313667)