Having done git fetch --all --prune
to fetch refs from the remote repositories I now want to see the most recent commit on each of the branches on origin
The command
git for-each-ref --format='%(refname:short)' | grep 'origin/'
lists all sixteen branches on origin
, and so I would expect the following command to show the most recent commit from each one
git for-each-ref --format='%(refname:short)' | grep 'origin/' |
xargs git log --source -n 1
(N.B. This is one line when I run it; I have split it over two for readability.)
However the command does not work, it only lists one commit: it seems the one commit limit applies to the entire list and not to each branch in turn.
What am I doing wrong?
(Note that I have also tried to adapt the solution here
git for-each-ref --format='%(refname:short)' | grep 'origin/' |
xargs git show --oneline
but the --oneline
flag is ignored and the result is too verbose.)
The problem is that git log only prints the log of one ref, that is why your xargs call is not working. If you e.g. call
git log -n 1 origin/master origin/not_master
(using xargs will result in a call like this) you'll get the log up to the most recent commit and that list is then limited to the first entry. I don't know what exactly will happen if the two branches have diverged, but still, you'll limit the complete log output to only one entry.Additionally to VonC's detailed answer, you can modify your command to achieve the desired result if you wrap the git log command in a loop instead of using xargs:
Use the --no-pager option to send the output directly to the console.
Combining Andrew C's comment on the original post, that the pattern matching can be included in the git command (instead of using grep), with andreas-hofmann's point (in his answer) that xargs is conflating arguments, then another possible solution is this
This swaps the pattern matching to occur in the git command and tells xargs to provide at most one argument at a time.
(N.B. The pattern matching in git's for-each-ref command goes from the start of the match so I have to use 'refs/remotes/origin/' instead of the pattern 'origin/' which I could use with grep. And I could replace --max-count=1 with -1 for brevity.)
A simpler solution is to use
git ls-remote origin
:For example, in the git repo:
That will list the most recent commits... even without fetching first!
That can be formatted and aliases easily:
Then a simple git rh would give:
That is:
This alias assume the remote is named 'origin' though.
To make it accept a parameter, it can be changed to a function:
Then: