Update TO script, and also some UI issues.
[git] / TO
1 #!/bin/sh
2
3 clean= next=next
4 while case $# in 0) break ;; esac
5 do
6         case "$1" in
7         --clean)
8                 branch=`git symbolic-ref HEAD` &&
9                 test refs/heads/master = "$branch" || {
10                         echo >&2 Not on master 
11                         exit 1
12                 }
13                 clean=t
14                 ;;
15         --next)
16                 test 2 -le $# || {
17                         echo >&2 "Need argument"
18                         exit 1
19                 }
20                 next="$2"
21                 git rev-parse --verify "$next" >/dev/null || exit
22                 shift
23                 ;;
24         *)
25                 echo >&2 "$0 [--clean | --next test-next ]"
26                 exit 1
27                 ;;
28         esac
29         shift
30 done
31
32 LF='
33 '
34 (cd .git/refs/heads && find -type f) |
35 sed -n \
36     -e 's/^\.\///' \
37     -e '/^[^\/][^\/]\//p' |
38 while read topic
39 do
40         rebase= done= not_done= trouble=
41
42         # (1)
43         only_next_1=`git-rev-list ^master "^$topic" ${next} | sort`
44         only_next_2=`git-rev-list ^master           ${next} | sort`
45         if test "$only_next_1" = "$only_next_2"
46         then
47                 not_in_topic=`git-rev-list "^$topic" master`
48                 if test -z "$not_in_topic"
49                 then
50                         rebase=" (vanilla)"
51                 else
52                         rebase=" (can be rebased)"
53                 fi
54         fi
55
56         # (2)
57         not_in_master=`
58                 git-rev-list --pretty=oneline ^master "$topic" |
59                 sed -e 's/^[0-9a-f]* //'
60         `
61         test -z "$not_in_master" &&
62         done="${LF}Fully merged -- delete."
63
64         # (3)
65         not_in_next=`
66                 git-rev-list --pretty=oneline ^${next} "$topic" |
67                 sed -e 's/^[0-9a-f]* / - /'
68         `
69         if test -n "$not_in_next"
70         then
71                 if test -n "$done"
72                 then
73                         trouble="${LF}### MODIFIED AFTER COOKED ###"
74                 fi
75                 not_done="${LF}Still not merged in ${next}$rebase.$LF$not_in_next"
76         elif test -n "$done"
77         then
78                 not_done=
79         else
80                 not_done="${LF}Up to date."
81         fi
82
83         echo "*** $topic ***$trouble$done$not_done"
84
85         if test -z "$trouble$not_done" &&
86             test -n "$done" &&
87             test t = "$clean"
88         then
89                 git branch -d "$topic"
90         fi
91 done
92
93 exit
94
95 ################################################################
96 Using Topic Branches
97
98 Some important disciplines first.
99
100  * Once a topic branch forks from "master", never merge "master"
101    updates into the topic branch.
102
103  * Once a topic branch is fully cooked and merged into "master",
104    delete it.  If you need to build on top of it to correct
105    earlier mistakes, create a new topic branch by forking at the
106    tip of the "master".  This is not strictly necessary, but it
107    makes it easier to keep your history simple.
108
109  * Whenever you need to test or publish your changes to topic
110    branches, merge them into "next" branch.
111
112 So, you would want to know:
113
114 (1) ... if a topic branch has ever been merged to "next".  Young
115     topic branches can have stupid mistakes you would rather
116     clean up, and things that have not been merged into other
117     branches can be easily rebased without affecting others.
118
119 (2) ... if a topic branch has been fully merged to "master".
120     Then you can delete it.  More importantly, you can tell you
121     should not build on top of it.
122
123 (3) ... if a topic branch has commits unmerged to "next".  You
124     need to merge them to test and/or publish.
125
126 Let's look at this example:
127
128                    o---o---o---o---o---o---o---o---o---o "next"
129                   /       /           /           /
130                  /   a---a---b A     /           /
131                 /   /               /           /
132                /   /   c---c---c---c B         /
133               /   /   /             \         /
134              /   /   /   b---b C     \       /
135             /   /   /   /             \     /
136     ---o---o---o---o---o---o---o---o---o---o---o "master"
137
138
139 A, B and C are topic branches.
140
141  * A has one fix since it was merged up to "next".
142
143  * B has finished.  It has been fully merged up to "master" and "next",
144    and is ready to be deleted.
145
146  * C has not merged to "next" at all.
147
148 To compute (1):
149
150         git-rev-list ^master ^topic next
151         git-rev-list ^master        next
152
153         if these match, topic has not merged in next at all.
154
155 To compute (2):
156
157         git-rev-list master..topic
158
159         if this is empty, it is fully merged to "master".
160
161 To compute (3):
162
163         git-rev-list next..topic
164
165         if this is empty, there is nothing to merge to "next".
166