dotclaude

Command in version-control

clean-branches

List local Git branches that are fully merged or stale and delete them safely after showing what would be removed, protecting main, master, develop, and the current branch. Pass --dry-run to preview. Unlike the finish-branch skill, which closes one active branch, this cleans up accumulated branches across the repository. Use when local branches have piled up and need safe cleanup.

Arguments
[--dry-run]
Model
inherit
Allowed tools
Bash(git:*)

Install

As a plugin

Bundled in the git plugin. Add the marketplace once, then install the bundle; it updates with the marketplace.

/plugin marketplace add KhaledSaeed18/dotclaude
/plugin install git@dotclaude

As a single item

Run from the project root; the command lands under .claude/. Copy it to ~/.claude/ to make it global.

npx shadcn@latest add KhaledSaeed18/dotclaude/clean-branches

Files installed

  • .claude/commands/clean-branches.md

What it does

Context

Options: $ARGUMENTS

Current branch and remotes:

!git branch --show-current 2>/dev/null

!git remote -v 2>/dev/null | head -4

Task

Identify merged and stale local branches and remove them, after presenting a clear list of what will be deleted and why.

Step 1: Gather branch state

# All local branches with their last commit date and whether they are merged into main/master
git branch -v --merged main 2>/dev/null || git branch -v --merged master 2>/dev/null
# Branches with no corresponding remote-tracking ref (orphaned after remote deletion)
git branch -vv | grep ": gone]"
# All local branches with last commit date, sorted oldest first
git for-each-ref --sort=committerdate refs/heads/ \
  --format="%(committerdate:short)  %(refname:short)  %(upstream:track)"

Step 2: Classify branches for deletion

Candidates for deletion are branches that meet one or more of these criteria:

  1. Fully merged: the branch tip is reachable from main or master (shown by git branch --merged).
  2. Remote gone: the tracking remote branch was deleted (shown by ": gone]" in git branch -vv).
  3. Stale and inactive: last commit is more than 90 days old and the branch has no open remote counterpart.

Protected branches - never delete:

  • main, master, develop, dev, staging, production
  • The currently checked-out branch
  • Any branch with uncommitted changes (this cannot happen for local branches, but note it as a constraint)

Build two lists:

  • Safe to delete: merged or remote-gone branches that are not protected.
  • Needs review: stale branches that are not merged and whose remote still exists (present these for manual decision, do not auto-delete).

Step 3: Confirm and act

Present the lists clearly before deleting anything:

Branches to delete (merged or remote-gone):
  feature/old-login     last commit: 2024-11-03  [merged into main]
  fix/typo-in-readme    last commit: 2025-01-14  [remote: gone]

Branches for manual review (stale, not merged):
  experiment/new-nav    last commit: 2024-09-12  [remote still exists]

If $ARGUMENTS contains --dry-run, stop here and print the lists without deleting anything.

Otherwise, ask: "Delete the N branches above? (yes/no)" and wait for confirmation before proceeding.

On confirmation, delete each safe branch:

git branch -d <branch-name>   # for merged branches (safe delete, errors if not merged)
git branch -D <branch-name>   # for remote-gone branches (force delete, only after showing the user)

Use -d (safe) for merged branches. Use -D (force) only for branches confirmed as remote-gone, and log each one explicitly.

Step 4: Report

After deletion, report:

  • How many branches were deleted
  • Whether any deletion failed and why
  • Any branches in the "needs review" list that the user should decide on manually

Optionally offer: git remote prune origin to also clean up stale remote-tracking refs if any were found.

This is the command as installed, rendered from its source on GitHub. Read it as Markdown.

  • commitCreate one well-formed commit from the current changes using the git-commit skill's rules: inspect the diff, honour the repo's commitlint and hooks, stage...
  • prTake the current branch from uncommitted work to an open pull request: commit outstanding changes with the git-commit rules if asked, push with upstream...
  • changelogGenerate a changelog or release notes from Git history, grouped by change type, written in user-facing language, with issue/PR links and breaking changes...
  • finish-branchWrap up a completed development branch by verifying tests pass, detecting the workspace state, then presenting clear merge / PR / keep / discard options...
  • git-commitCommit work the right way by gathering full repo state, respecting the project's commitlint/pre-commit/branch rules, staging only understood files, and...
  • git-undoRecover safely from Git mistakes such as discard, unstage, amend, reset, revert, restore lost commits via reflog, recover deleted branches, and fix bad...