I know I can do git branch --all
, and that shows me both local and remote branches, but it's not that useful in showing me the relationships between them.
How do I list branches in a way that shows which local branch is tracking which remote?
I know I can do git branch --all
, and that shows me both local and remote branches, but it's not that useful in showing me the relationships between them.
How do I list branches in a way that shows which local branch is tracking which remote?
Very much a porcelain command, not good if you want this for scripting:
git branch -vv # doubly verbose!
Note that with git 1.8.3, that upstream branch is displayed in blue (see "What is this branch tracking (if anything) in git?")
If you want clean output, see Carl Suster's answer - it uses a porcelain command that I don't believe existed at the time I originally wrote this answer, so it's a bit more concise and works with branches configured for rebase, not just merge.
bugs/bug1234
. To fix this, I removed the: refs/heads/*
part from the command. –
Linebacker grep '^refs/heads'
if you want to include branches with slashes in their names. –
Czerny refs/heads/
–
Linebacker git branch -vv
still working on git 2.16? When I run that command it does only list the branchname followed by a short SHA1 and its last commit's comment –
Undergo git for-each-ref --format='%(refname:short) : %(upstream:short)' refs/heads/*
–
Stonge -vv
the default option using .gitconfig
? –
Goodard --list $currentBranchName
, e.g.: git branch -vv --list master
–
Speech configured for 'git push'
and whose remote counterpart is tracked
according to git remote show origin
. Indeed, if I push from it (with no arguments), the local branch is pushed to the remote. But git branch -vv
does not list a remote branch for my local one. So, this answer seems wrong. –
Adkinson git branch -v
–
Radioactivity alias br = branch -vv
. I like having short-name aliases for common commands, and I know that I will never remember -vv
, so it's a natural fit for the alias. –
Statement git branch -vv
isn't remotely useful as it continues to list remotes after they have been deleted. –
Semantic git fetch --prune
–
Beaufort git remote show origin
Replace 'origin' with whatever the name of your remote is.
git remote show
command actually connects to the remote repo... and hence it fails if you happen to be off-line or unable to connect to the repo for whatever reason... –
Stephi git remote show -n origin
to get some information even when offline. From the git remote documentation: "With -n option, the remote heads are not queried first with git ls-remote <name>; cached information is used instead." –
Atalanti git remote show | xargs git remote show -n
to view combined tracking info for all remotes. –
Euraeurasia git remote show
lists as untracked? It looks like this command shows what will happen when I do git push
/git pull
, rather than whether branches are tracked. –
Bremerhaven If you look at the man page for git-rev-parse
, you'll see the following syntax is described:
<branchname>@{upstream}
, e.g.master@{upstream}
,@{u}
The suffix
@{upstream}
to a branchname (short form<branchname>@{u}
) refers to the branch that the branch specified by branchname is set to build on top of. A missing branchname defaults to the current one.
Hence to find the upstream of the branch master
, you would do:
git rev-parse --abbrev-ref master@{upstream}
# => origin/master
To print out the information for each branch, you could do something like:
while read branch; do
upstream=$(git rev-parse --abbrev-ref $branch@{upstream} 2>/dev/null)
if [[ $? == 0 ]]; then
echo $branch tracks $upstream
else
echo $branch has no upstream configured
fi
done < <(git for-each-ref --format='%(refname:short)' refs/heads/*)
# Output:
# master tracks origin/master
# ...
This is cleaner than parsing refs and config manually.
done < <(git for-each-ref --format='%(refname:short)' refs/heads/**)
Note the two asterisks at the end of the glob pattern. –
Krishnakrishnah git rev-parse --abbrev-ref HEAD@{upstream}
seems to work nicely for the current branch. It also makes for a nice git alias. –
Mestizo while
loop syntax looks a bit weird to me. You can just use git for-each-ref ... | while read branch; do ...
which doesn't need a FIFO and runs in the same order like the commands written. –
Crayon git for-each-ref --format='%(refname:short) tracks %(upstream:short)' refs/heads/*
–
Stonge An alternative to kubi's answer is to have a look at the .git/config
file which shows the local repository configuration:
cat .git/config
git config --get-regex branch
–
Unbosom branch.NAME.remote
and branch.NAME.merge
are set... –
Bremerhaven git for-each-ref --format='%(refname:short) <- %(upstream:short)' refs/heads
will show a line for each local branch. A tracking branch will look like:
master <- origin/master
A non-tracking one will look like:
test <-
git branch -vv
. 🙏 –
Manilla git config --global alias.track 'for-each-ref --format='\''%(refname:short) <- %(upstream:short)'\'' refs/heads'
–
Manilla For the current branch, here are two good choices:
% git rev-parse --abbrev-ref --symbolic-full-name @{u}
origin/mainline
or
% git for-each-ref --format='%(upstream:short)' $(git symbolic-ref -q HEAD)
origin/mainline
That answer is also here, to a slightly different question which was (wrongly) marked as a duplicate.
git for-each-ref --shell --format='%(refname:short) %(upstream:short)' refs/heads
. –
Selfexplanatory For the current branch, you could also say git checkout
(w/o any branch). This is a no-op with a side-effects to show the tracking information, if exists, for the current branch.
$ git checkout
Your branch is up-to-date with 'origin/master'.
git checkout .
, which is not a no-op. –
Boughton Here is a neat and simple one. Can check git remote -v
, which shows you all the origin and upstream of current branch.
git push
(without specifying any remote branch name) from inside that feature branch. You can set the remote branch a feature branch should push to by default via git push -u origin remoteFeatureBranchName
. Generally, remoteFeatureBranchName will be the same name as the local feature branch you are pushing from, but it need not be. the command you suggest does not show this connection; it shows the origin and upstream repos, but not the linked branches. –
Tad I use this alias
git config --global alias.track '!f() { ([ $# -eq 2 ] && ( echo "Setting tracking for branch " $1 " -> " $2;git branch --set-upstream $1 $2; ) || ( git for-each-ref --format="local: %(refname:short) <--sync--> remote: %(upstream:short)" refs/heads && echo --Remotes && git remote -v)); }; f'
then
git track
Based on Olivier Refalo's answer
if [ $# -eq 2 ]
then
echo "Setting tracking for branch " $1 " -> " $2
git branch --set-upstream $1 $2
else
echo "-- Local --"
git for-each-ref --shell --format="[ %(upstream:short) != '' ] && echo -e '\t%(refname:short) <--> %(upstream:short)'" refs/heads | sh
echo "-- Remote --"
REMOTES=$(git remote -v)
if [ "$REMOTES" != '' ]
then
echo $REMOTES
fi
fi
It shows only local with track configured.
Write it on a script called git-track on your path an you will get a git track command
A more elaborated version on https://github.com/albfan/git-showupstream
git config --get-regexp "branch\.$current_branch\.remote"
will give you the name of the remote that is being tracked
git config --get-regexp "branch\.$current_branch\.merge"
will give you the name of the remote branch that's being tracked.
You'll need to replace $current_branch with the name of your current branch. You can get that dynamically with git rev-parse --abbrev-ref HEAD
The following mini-script combines those things. Stick it in a file named git-tracking
, make it executable, and make sure it's in your path.
then you can say
$ git tracking
<current_branch_name>-><remote_repo_name>/<remote_branch_name>
note that the remote branch name can be different from your local branch name (although it usually isn't). For example:
$git tracking
xxx_xls_xslx_thing -> origin/totally_bogus
as you can see in the code the key to this is extracting the data from the git config. I just use sed to clear out the extraneous data.
#!/bin/sh
current_branch=$(git rev-parse --abbrev-ref HEAD)
remote=$(git config --get-regexp "branch\.$current_branch\.remote" | sed -e "s/^.* //")
remote_branch=$(git config --get-regexp "branch\.$current_branch\.merge" | \
sed -e "s/^.* //" -e "s/refs\/.*\///")
echo "$current_branch -> $remote/$remote_branch"
Get info about all remotes, branches and tracking:
for remote in $(git remote show -n); do git remote show -n "${remote:?}"; done
or get just names of remotes with their url
git remote -v show -n
© 2022 - 2024 — McMap. All rights reserved.