As a Team Lead I want to see a clean git repository with branches, which are currently in development and not to see list of 3000+ branches, which was created from the first day of the project. Manual investigation and removing of obsolete branches will take ages, so I created few bash scripts, which will do the work automatically.
First script defines all branches, which are already merged in master
, and removes them from remote repository:
1
2
3
4
|
git fetch -p
git fetch --all
git branch | grep -v "master" | xargs git branch -D
git branch -a --merged remotes/origin/master | grep -v "master\|stage\|uat" | grep "remotes/origin/" | cut -d "/" -f 3- | xargs -n 1 git push --delete origin
|
Second script will help us to find obsolete branches. We will try to merge master branch in all other branches, and failed merge will inform us that such branch is a good candidate for removing. Script will output all failed merges to /tmp/merge_fail.log
file.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
|
file_log="/tmp/merge_fail.log"
# Remove log file if it already exist
if [ -f $file_log ];then
sudo rm -f /tmp/merge.log
fi
# Checkout to master and update branch
sudo git checkout master
sudo git pull
# Remove all local branches
sudo /bin/bash -c 'git branch | grep -v "master" | xargs git branch -D'
# Iterate all unmerged to master branches
for BRANCH in `git branch -r --no-merged master`;
do
LOCALBRANCH=$(echo $BRANCH | sed -r 's/^.{7}//');
echo $LOCALBRANCH;
# Hard reset and clean of current branch
sudo git reset --hard HEAD > /dev/null;
sudo git clean -fdx > /dev/null;
# Checkout on branch in which master must be merged
sudo git checkout $LOCALBRANCH > /dev/null;
# Merge
failed_merge=$(sudo git merge origin/master --no-edit|grep 'merge failed'|grep 'fix conflicts')
clearBranch=$(echo $BRANCH |awk -F '/' '{print $2}')
# Write merge failed branches to log file
if [ ! -z "$failed_merge" ];then
echo -e "${clearBranch}" >> $file_log
fi
# Abort merge if something goes wrong
sudo git merge --abort > /dev/null;
done
|
P.S. Last script can be used in CI pipeline as “backward automerge” step, to do this just add to the bottom git command which will push all merged branches into origin:
1
2
|
# Push all merges to origin
sudo git push --all origin
|