git branch --merged main | grep -vE '^\*|main|develop' | xargs -r git branch -d удаляет все локальные ветки, уже влитые в main, кроме main и develop. Ветки, слитые через squash merge, эта команда не тронет: git никогда не записывает их коммиты как влитые, поэтому --merged их не замечает — проверяйте git branch -vv на отметку gone.
1. Сначала посмотреть, что считается слитым
$ clai покажи ветки, слитые в main→ git branch --merged main feature-merged* main
Список для чтения. Текущая ветка помечена звёздочкой, её удалить нельзя — и не нужно.
2. Удалить, защитив главные ветки
$ clai удали локальные ветки, слитые в main, кроме main и develop→ git branch --merged main | grep -vE '^\*|main|develop' | xargs -r git branch -dВетка feature-merged удалена (была fb52fec).
-d безопасен: git откажется удалять ветку с несмерженными коммитами. Фильтр grep -vE обязателен, иначе в список попадёт сама main. -r не даёт xargs запуститься на пустом списке.
3. Проверить, что лишнее не удалилось
$ clai покажи оставшиеся ветки→ git branch feature-open* main
feature-open содержит несмерженные коммиты и осталась на месте. Это и есть проверка того, что фильтр сработал правильно.
4. Ловушка: squash merge прячется от --merged
$ clai покажи ветки, у которых удалён upstream на сервере→ git fetch --prune && git branch -vv | grep '\[.*: gone\]'
Вот главное. При squash merge коммиты ветки не попадают в историю main как есть, поэтому --merged её не покажет — она останется у вас навсегда. Но её upstream на сервере удалён после мержа пул-реквеста, и git branch -vv помечает такую ветку как gone. Это надёжный признак.
5. Удалить ветки с исчезнувшим upstream
$ clai удали локальные ветки, ветка-источник которых удалена на сервере→ git fetch --prune && git branch --format '%(refname:short) %(upstream:track)' | awk '$2 == "[gone]" {print $1}' | xargs -r git branch -D⚠ CAUTION — this is -D, not -d: it also deletes unmerged branches
-D нужен именно потому, что git не считает squash-слитые ветки смерженными и откажет на -d. Плата за это — прочитайте список из предыдущей команды до того, как запустите эту.
6. Подчистить ссылки на удалённые ветки сервера
$ clai убери ссылки на ветки, которых уже нет на сервере→ git remote prune origin
Удаляет только локальные ссылки origin/*, ваши ветки не трогает. Полезно, когда автодополнение предлагает ветки, закрытые полгода назад.
Грабли
-dи-D— разные уровни риска. Строчная удаляет только слитое, заглавная удаляет что угодно. Для squash-веток нужна заглавная, поэтому сначала список, потом удаление.--mergedбез аргумента считает от текущей ветки. Стоя на feature-ветке вы получите совсем другой список. Указывайте базу явно:--merged main.- Удалённая локальная ветка не удаляется на сервере. Для этого нужен
git push origin --delete имя. И наоборот: удаление на сервере не убирает вашу локальную копию.
Похожие вопросы
Как вернуть случайно удалённую ветку? git reflog покажет её последний коммит, дальше git branch имя <хеш>. Работает, пока не отработала сборка мусора.
Почему ветка не удаляется? Либо вы на ней стоите — перейдите на main, либо в ней есть несмерженные коммиты и -d защищает вас от потери.
Как посмотреть, когда ветка последний раз обновлялась? git branch --sort=-committerdate -v отсортирует по свежести — удобно, чтобы найти заброшенные.
Читайте также
- Отменить последний коммит в git, сохранив изменения
- Удалить секрет из истории git
- Git-задачи как мысль вслух
CliAI превращает формулировки выше в точную команду и показывает её перед запуском — шаг с -D получает пометку CAUTION, а не тихий запуск. Установка одной строкой.