Using a user-specific conf that wasn't owned by the SSH user wasn't working out.
[git-central.git] / server / update-prefer-rebase
1 #!/bin/sh
2 #
3 # Watches for merges that had only local merges (e.g. should have been rebases).
4 #
5 # If they are introducing non-merge commits /and/ merge commits, it could
6 # look like one of two ways. This way:
7 #
8 # * --- B --- * --- oldrev
9 #        \             \
10 #        new --- new --- newrev
11 #
12 # They basically had an un-shared local dev branch (probably by making a
13 # merge) and instead should have done a rebase. Also, if they did:
14 #
15 # * --- B --- * --- oldrev
16 #        \             \
17 #        new --- new --- new -- newrev
18 #
19 # We should try and catch them--where the merge happened previously to
20 # them doing more work in the newrev commit.
21 #
22 # But if it looks like:
23 #
24 # * --- B --- * --- oldrev
25 #        \              \
26 #        old --- new --- newrev
27 #
28 # Then they had a pre-shared branch that cannot be rebased and so they
29 # were correct in doing a merge to tie "old" and "oldrev" together.
30 #
31 # Also, we obviously have to be okay with:
32 #
33 # * --- * --- * --- oldrev --- new --- new --- newrev
34
35 # Command line
36 refname="$1"
37 oldrev="$2"
38 newrev="$3"
39
40 if expr "$oldrev" : '0*$' >/dev/null ; then
41         exit 0
42 fi
43
44 # Read backwards: all commits from old..new, unless they are already referenced by a branch
45 git rev-parse --not --branches | git rev-list --stdin $oldrev..$newrev | while read commit ; do
46         number_of_parents=$(git rev-list -n 1 --parents $commit | sed 's/ /\n/g' | grep -v $commit | wc -l)
47         if [[ $number_of_parents > 1 ]] ; then
48                 # Find the original branch point (B)
49                 parents=$(git rev-list -n 1 --parents $commit | sed 's/ /\n/g' | grep -v $commit)
50                 baserev=$(git merge-base $parents)
51
52                 # For each parent
53                 git rev-list -n 1 --parents $commit | sed 's/ /\n/g' | grep -v $commit | while read parent ; do
54                         all_commits=$(git rev-list $baserev..$parent | wc -l)
55                         new_commits=$(git rev-parse --not --branches | git rev-list --stdin $baserev..$parent | wc -l)
56                         if [[ $all_commits -eq $new_commits ]] ; then
57                                 echo "----------------------------------------------------"
58                                 echo
59                                 echo "It looks like you should rebase instead of merging $commit"
60                                 echo
61                                 echo "----------------------------------------------------"
62                                 exit 1
63                         fi
64                 done
65                 if [ $? -ne 0 ] ; then
66                         exit 1
67                 fi
68         fi
69 done
70