summaryrefslogtreecommitdiffstats
path: root/switch_all_submodules_to_head_and_clean
blob: 5ca3d13b03bad3da21a122b8699fa68ac279c4f8 (plain)
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
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
#!/bin/bash

# echo in bold
echobd () {
    if [ -p /dev/stdout ]; then
        echo "$1"
    else
        echo -ne "\033[1m"
        echo -n "$1"
        echo -e "\033[0m"
    fi
}

# verify git directory and branch
if [[ ! -e .git ]] &&
   [[ -z "`git rev-parse --git-dir 2>/dev/null`" ]]; then
	echo "Current directory does not contain a .git folder.  Exiting..."
	exit 1
fi

branch=`git symbolic-ref -q HEAD | sed "s|^refs/heads/||"`
if [[ -z "$branch" ]]; then
    branch=`git branch --contains HEAD | egrep -v "no branch|detached" | head -n1 | cut -c 3-`
fi
if [[ -z "$branch" ]]; then
	echo "There is not active branch.  Exiting..."
	exit 1
fi
remote=`git config branch."$branch".remote`
if [[ -z "$remote" ]]; then
	echo "Active branch is not remote tracked.  Exiting..."
	exit 1
fi

# get git user
echobd "Preparing $(git rev-parse --show-toplevel | xargs -r basename) $branch branch for development use"
if [[ $1 == "" ]]; then
	gituser=`git config --local remote.$remote.url | sed -n "s|\(https\?://\)\?\([^@]*\)@.*|\2|p" | grep -v "\(anonymous\|system\)"`
else
	gituser=$1
fi

if [[ $gituser == "" ]]; then
	read -p "Enter your TDE GIT username []: " -e gituser
fi

if [[ $gituser == "" ]]; then
	gituser="anonymous"
fi

# check git abilities
if [[ -n "`git status --help 2>/dev/null|grep -- '--ignore-submodules'`" ]]; then
  GIT_IGNORE_SUBMODULES="--ignore-submodules"
fi
if [[ -n "`git pull --help |grep -- '--\[no-\]recurse-submodules'`" ]]; then
  GIT_NO_RECURSE_SUBMODULES="--no-recurse-submodules"
fi

# update module and submodules
updateModule() {
    local MODULE
    local REPO_URL
    local REPO_PROTO
    local REPO_MODULE
    local REPO_WORKTREE
    if [[ "$1" != "" ]]; then
        MODULE=$1/
    else
        MODULE=""
    fi

    cd $PARENTDIR/$MODULE
    if [[ ! -z "`git status --porcelain $GIT_IGNORE_SUBMODULES`" ]]; then
        git reset --hard HEAD
        git clean -dxff
    fi
    git remote |
    while read REMOTE; do
      REPO_SERVER=$(git config remote."$REMOTE".url |
                    sed -n "s|^http[^/]*/*\([^@]*@\)\?\([^/]*\)/.*|\2|p")
      if [ -x /usr/bin/fping ] && [ -n "$REPO_SERVER" ]; then
        fping -q -r1 "$REPO_SERVER" || continue
      fi
      echo Fetching $REMOTE
      git fetch $REMOTE --prune $GIT_NO_RECURSE_SUBMODULES
    done
    git branch | grep -x "* $branch" >/dev/null || \
    git checkout $branch
    remote=`git config branch."$branch".remote`
    [[ -n "$remote" ]] || return
    git rebase $remote/$branch $branch
    if [[ ! -z "`git status --porcelain $GIT_IGNORE_SUBMODULES`" ]]; then
        git reset --hard HEAD
        git clean -dxff
    fi

    if [[ -e $PARENTDIR/$MODULE.gitmodules ]]; then
        if [[ $gituser == "anonymous" ]]; then
            sed -i 's/system@//g' $PARENTDIR/$MODULE.gitmodules
        else
            sed -i "s/system@/$gituser@/g" $PARENTDIR/$MODULE.gitmodules
        fi
        REPO_URL=$(git config --get remote.$remote.url |\
                   sed "s|\(https\?://\)\?\([^@]*@\)\?\(.*\)/[^/]*$|\3|")
        REPO_PROTO=$(git config --get remote.$remote.url |\
                     sed "s|\(https\?://\)\?\([^@]*@\)\?\(.*\)/[^/]*$|\1|")
        REPO_MASTER=scm.trinitydesktop.org/scm/git
        REPO_MODULE=$(git config --get remote.$remote.url |\
                      sed -e "s|\(https\?://\)\?\([^@]*@\)\?\(.*\)/\([^/]*\)$|\4|" -e "s|\.git$||")
        REPO_GITDIR=$(git rev-parse --git-dir)
        if [[ "${REPO_GITDIR/worktrees//}" != "$REPO_GITDIR" ]]; then
            REPO_WORKTREE=${REPO_GITDIR%/[^/]*/worktrees/[^/]*}
        fi
        if [[ "$REPO_URL" != "$REPO_MASTER" ]]; then
            sed -i "s#https\?://\([^@]*@\)\?$REPO_MASTER#$REPO_PROTO\1$REPO_URL#g" $PARENTDIR/$MODULE.gitmodules
        fi
        sed -n "s|^\[submodule \"\([^\"]*\)\"\]$|\1|p" <$PARENTDIR/$MODULE.gitmodules |\
        while read submodule; do
            echobd "Attempting to switch submodule ${MODULE}${submodule}"
            cd $PARENTDIR/$MODULE
            if [[ -n "$REPO_WORKTREE" ]] && [[ ! -e "$submodule/.git" ]]; then
                REPO_LOCALTREE=$(git config --file .gitmodules --get submodule.$submodule.url | \
                                 sed "s#^\(https\?://\)\?\([^@]*@\)\?$REPO_URL#$REPO_WORKTREE#g")
                if [[ ! -d "$REPO_LOCALTREE" ]]; then
                    REPO_LOCALTREE=$REPO_LOCALTREE.git
                fi
                if [[ ! -d "$REPO_LOCALTREE" ]]; then
                    git clone --bare --config "remote.origin.fetch=+refs/heads/*:refs/remotes/origin/*" \
                        "$(git config --file .gitmodules --get submodule.$submodule.url)" "$REPO_LOCALTREE"
                fi
                if [[ "$REPO_MODULE" != "tde" ]]; then
                    git config --file .gitmodules submodule.$submodule.url "$REPO_LOCALTREE"
                else
                  (
                    cd $REPO_LOCALTREE &&
                    git fetch &&
                    git worktree add $PARENTDIR/$MODULE$submodule $branch &&
                    cd $PARENTDIR/$MODULE$submodule &&
                    git branch --set-upstream-to=origin/$branch
                  ) || continue
                fi
            fi
            if [[ -z "`git config --get submodule.$submodule.url`" ]]; then
                git submodule init -- $submodule
            fi
            if [[ ! -e "$submodule/.git" ]]; then
                git submodule update -- $submodule
            fi
            updateModule ${MODULE}${submodule}
        done
        git checkout -- $PARENTDIR/$MODULE.gitmodules
    fi
}

# Update from top module
cd `git rev-parse --show-toplevel`
PARENTDIR=$PWD
echobd "Working in $PARENTDIR"
updateModule
echobd "Done in $PARENTDIR"