# git branch -d / -D: Usage, Options & Common CI Errors

> git branch -d deletes a merged branch; -D force-deletes any branch. Reference for the not-fully-merged error, deleting the current branch, and CI cleanup.

Source: https://latchkey.dev/learn/command-reference/git-branch-delete  
Updated: 2026-06-25

git branch -d safely deletes a merged branch; -D forces deletion regardless of merge state.

Branch cleanup is routine after merges. The -d/-D distinction is a safety gate: -d refuses to drop unmerged work, while -D overrides that check.

## What it does

git branch -d deletes a local branch only if it is fully merged into its upstream or HEAD. git branch -D (a synonym for --delete --force) deletes it unconditionally, discarding any commits unique to it.

## Common usage

```Terminal
git branch -d feature           # only if merged
git branch -D feature           # force, even if unmerged
git branch -d -r origin/old     # delete a remote-tracking ref locally
git branch --merged main | grep -v '\*' | xargs -r git branch -d
```

## Options

| Flag | What it does |
| --- | --- |
| -d / --delete | Delete a merged branch |
| -D | Force-delete (delete + force) |
| -r | Operate on remote-tracking refs |
| --merged / --no-merged | Filter branches by merge state |

## Common errors in CI

error: The branch 'X' is not fully merged. If you are sure you want to delete it, run 'git branch -D X' - -d protects unmerged commits; use -D to override. error: Cannot delete branch 'X' checked out at '<path>' means it is the current branch or used by a worktree; switch away first.

## Using this in CI

CI checkouts are shallow and detached by default, which changes the answer this command gives you. Commands that read history, branch names, or tags need the checkout configured for it.

```.github/workflows/ci.yml
- uses: actions/checkout@v4
  with:
    fetch-depth: 0   # history, tags, and git describe all need this

- run: |
    git rev-parse --is-shallow-repository   # expect false
    git rev-parse --abbrev-ref HEAD          # prints HEAD when detached
```

> `git rev-parse --abbrev-ref HEAD` returns the literal string `HEAD` on a detached checkout rather than a branch name. On GitHub Actions read `github.ref_name` instead; the git command cannot know what it was checked out for.

## FAQ

### git branch -d / -D: Usage, Options & Common CI Errors?

Branch cleanup is routine after merges. The -d/-D distinction is a safety gate: -d refuses to drop unmerged work, while -D overrides that check.

### What it does?

git branch -d deletes a local branch only if it is fully merged into its upstream or HEAD. git branch -D (a synonym for --delete --force) deletes it unconditionally, discarding any commits unique to it.

### Common errors in CI?

error: The branch 'X' is not fully merged. If you are sure you want to delete it, run 'git branch -D X' - -d protects unmerged commits; use -D to override. error: Cannot delete branch 'X' checked out at '<path>' means it is the current branch or used by a worktree; switch away first.

---

Latchkey runs CI/CD that repairs its own failures. Agent entry points: https://latchkey.dev/agent.txt, https://latchkey.dev/openapi.json, https://latchkey.dev/llms.txt
