I am writing to a script to list all the git repositories on my system, their branches, and the latest commits on the system. So I have created this script prints out the following.
directory, branch(ref), date, commit hash, date, commit message, ref (again)
.
#!/bin/bash
IFS='
'
for directory in `ls -d $1/*/`; do
# echo "$directory : $directory.git"
if [[ -d $directory/.git ]] ; then
# filter=/refs/heads
filter=''
for branch in $(git -C $directory for-each-ref --format='%(refname)' $filter); do
echo $directory : $branch : "$(git -C $directory log -n 1 --oneline --pretty=format:'%Cred%h - %C(yellow)%ai - %C(green)%s %C(reset) %gD' $branch)" : $(echo $branch | rev | cut -d\/ -f-1 | rev)
done
fi
done
What I don't have is the repository URLs for the remotes. Can the remote's URL be printed as part of the output of git for-each-ref
command?
I guess I could use git remote -C $directory -v
to list the remotes for the repository into a lookup list which I would use for each value of xxxxx
in refs/remotes/xxxxx
into a variable which would be added to the echo
command.
You can use git for-each-ref
to generate an arbitrary script that will later be evaluated with eval
. Adapting to your case the longest of the examples from the documentation on git for-each-ref
, I arrived at the following:
#!/bin/bash
IFS='
'
for directory in "$1"/*/ ; do
# echo "$directory : $directory.git"
if [[ -d $directory/.git ]] ; then
# filter=/refs/heads
filter=''
fmt="
dir=$directory"'
ref=%(refname)
refshort=%(refname:short)
h=%(objectname:short)
date=%(authordate:iso)
subj=%(subject)
printf "%s : %s : %s - %s - %s : %s" "$dir" "$ref" %(color:red)"$h" %(color:yellow)"$date" %(color:green)"$subj" %(color:reset)"$refshort"
if [[ $ref == refs/remotes/* ]]
then
remotename="${ref#refs/remotes/}"
remotename="${remotename%%/*}"
printf " : %s" "$(git -C "$dir" remote get-url "$remotename")"
fi
printf "\n"
'
eval="$(git -C $directory for-each-ref --shell --format="$fmt" $filter)"
eval "$eval"
fi
done
Note that I got rid of the git log
from your implementation, but as a result I also dropped the %gD
field, since I didn't quite well understand what it meant, and couldn't find how to obtain it inside git-for-each-ref
. Besides, I changed the way of obtaining the short ref from the full ref; my implementation is not equivalent yours, but produces unambiguous results).