Filip Nilsson
Filip Nilsson

Reputation: 115

Track all local branches against remote

I did something fishy with my local repo a while back, which caused all my local branches to lose their remote tracking. I think I have my remote set up properly since I can see all remote branches and also add tracking to them.

When I create new branches locally it works fine.

This is the output of git branch -llv:

$ git branch -lvv Branch 1 d6c67c8 [origin/Branch 1] Commit message Branch 2 17503c9 Commit message Branch 3 4f987c4 Commit message Branch 4 6e5670a [origin/Branch 4] Commit message Branch 5 77bd14c Commit message

My question is wether I can add tracking between all my local branch_x and the remote equivalent origin/branch_x with one command? Since I have a lot of branches it seems quite cumbersome to do it one by one. The remotes might very well be ahead of my local branch in many of the cases, but probably not the majority of the cases.

I was thinking of doing something like git push -u origin --all, but I'm not sure if that's the best approach.

Upvotes: 0

Views: 482

Answers (2)

Superlexx
Superlexx

Reputation: 181

Here's another form of the accepted answer, letting git strip the paths and dropping the bash array. Also, not attempting to track the master branch (as it's usually implicit) or HEAD. Replace the last line with less to preview the commands.

git for-each-ref --shell --format='[[ %(refname) =~ /master$ ]] \
  || [[ %(refname) =~ /HEAD$ ]] \
  || git branch --track %(refname:lstrip=3) %(refname)' refs/remotes/origin |
    while read line; do eval "${line}"; done

Upvotes: 0

Tomasz Kaminski
Tomasz Kaminski

Reputation: 910

The only thing I could advice is the following:

git branch --set-upstream-to origin/your_branch

sets it for one branch.

Now, you would have to write a bash script that would for each branch would do:

git checkout $your_branch
git branch --set-upstream-to origin/$your_branch

One other thing:

branches=()
eval "$(git for-each-ref --shell --format='branches+=(%(refname))' refs/heads/)"
for branch in "${branches[@]}"; do
     echo $branch
done

Would print for you names of all the branches you have, prefixed by /refs/heads You can use this in your script.  

In fact your problem should be solved by running:

branches=()
eval "$(git for-each-ref --shell --format='branches+=(%(refname))' refs/heads/)"
for branch in "${branches[@]}"; do
     branch_name=`echo $branch | "sed s|refs/heads/||"`
     git checkout $branch_name
     git branch --set-upstream-to origin/$branch_name
done

Upvotes: 1

Related Questions