C.W.K.
Stream
Lesson 05 of 05 · published

Branch Hygiene: Naming, Deleting, and Pruning

~16 min · branch, cleanup

Level 0Untracked Rookie
0 XP0/47 lessons0/14 achievements
0/100 XP to next level100 XP to go0% complete

Branches are cheap to make and to delete

Branch hygiene is the housekeeping that keeps a repo readable a year in. The principle: make new branches without ceremony, but delete them once the work has landed. A repo with 200 stale branches is functionally a junk drawer; a repo with the active dozen is a workspace. The rule scales: project, team, and personal repos all benefit.

Naming pulls weight here. Most teams use prefix-based namespaces: feature/, bugfix/, hotfix/, release/, chore/, experiment/. The shape feature/short-summary reads in git branch -a output and groups well in tools. Add an issue or ticket reference when you have one: feature/142-oauth-github. Avoid generic names like my-changes, fix, or test — they collide and tell you nothing.

Deletion has two flavors. git branch -d feature/login deletes only if the branch is fully merged into its upstream — Git checks for you. git branch -D force-deletes regardless. Use -d by default; -D is for branches you intentionally abandoned without merging. After deleting locally, push the deletion to keep the remote tidy: git push origin --delete feature/login. GitHub also has an "auto-delete head branches after merge" setting that does this for PR-based workflows.

Pruning is the cleanup nobody schedules but everybody needs. git remote prune origin removes remote-tracking refs whose upstream branches no longer exist on origin. git fetch --prune does the same as part of normal fetch — set git config --global fetch.prune true and forget about it. git branch --merged main lists local branches fully merged into main, perfect candidates for deletion. Run that occasionally and the repo stays readable.

Code

Naming and listing·bash
# Common namespaces:
git switch -c feature/profile-page
git switch -c bugfix/login-crash
git switch -c hotfix/security-2026-04
git switch -c chore/update-deps
git switch -c experiment/new-rendering

# List local + remote branches by namespace:
git branch -a | sort

# Most-recently-touched branches first (great for finding stale ones):
git for-each-ref --sort=-committerdate refs/heads/ --format='%(refname:short)' | head -20
Delete and prune·bash
# Delete fully merged local branch (safe):
git branch -d feature/profile-page

# Force-delete unmerged local branch (intentionally abandon):
git branch -D experiment/dead-end

# Delete on the remote:
git push origin --delete feature/profile-page

# Auto-prune dead remote-tracking refs on every fetch:
git config --global fetch.prune true
git fetch                                   # now also prunes
git remote prune origin                     # explicit prune

# Show local branches already merged into main (delete candidates):
git branch --merged main | grep -v '\* main'

External links

Exercise

On a repo with at least one merged feature branch, run git branch --merged main. Delete one merged branch with git branch -d and the matching remote with git push origin --delete. Then enable fetch.prune = true globally. Run git for-each-ref --sort=-committerdate refs/heads/ and identify three more candidates for deletion based on age and merged status.

Progress

Progress is local-only — sign in to sync across devices.
Spotted a bug or have feedback on this page?Report an Issue

Comments 0

🔔 Reply notifications (sign in)
Sign inPlease sign in to comment.

No comments yet — be the first.