git submodules statistics in the terminal prompt
When I'm working in projects with submodules and I make a change in one of the submodules I have to go to every submodule directory to review the changes, some times I didn't make any change in a submodule but my memory is not that smart to know that and it's a waste of time.
The solution I found was to add some aliases to my ~/.gitconfig that help me to know the status of the submodules and to add the stats (amount of modified files) to my terminal prompt.
We'd need to add the aliases to the ~/.gitconfig file, if you don't have it, create it
$ mkdir ~/.gitconfig
now we'll need a [alias] key to add our aliases, we'll add them all just below it.
[alias] alias_1=... alias_2=... alias_n=...
Let's say we have 3 submodules in our project: Silence, Foo and Bar.
1. Alias to show the modified files in each submodule
substatus = "!git submodule foreach git ls-files -m"
the output would be somewhat like this:
$ git substatus
Entering 'Silence'
src/com/vo/LoremVO.as
Entering 'Foo'
Entering 'Bar'
bar.rb
baz.rb
NOTE: substatus is not a git status, it won't show either untracked nor staged files, it will only show modified files, please see the ls-files command help (git ls-files -h)
2. Alias to show the amount of modified files in all the submodules
substat = "!git submodule --quiet foreach 'echo $path: `git ls-files -m | wc -l`'"
the output would be somewhat like this:
$ git substat Silence: 1 Foo: 0 Bar: 2
if you see the output of git substatus you'll see that the amount of files matches.
3. Show the amount of modified files in all the submodules in the prompt
Add the following function to your ~/.bash_profile or ~/.bashrc (if you want to know what's the difference click here)
function __git_submodule_stat
{
if [ -d .git ]; then
stat=`git submodule --quiet foreach git ls-files -m | wc -l | tr -d ' '`
if [ $stat -eq 0 ]; then return; fi
echo "["$stat"]"
fi
}
then set your PS1
PS1="[\u:\h \W ] $(__git_ps1)$(__git_submodule_stat) $ "
and your prompt would be shown this way:
[user:host folder ] (master)[3] $ _
which would mean you are in the master branch of your repository and that there are 3 modified files in the submodules.
In this case I don't care about what submodule have been modified, I only want to know if there are modified files in any of the submodules, if so, then I use git substatus to know exactly which ones are the modified files.
The foreach argument to git submodule command is pretty interesting, it executes every command you pass it as parameter, such parameter might be a bash or ruby script with any amount of commands as well.
$ git submodule foreach ~/my_script.sh $ git submodule foreach ~/my_script.rb
If you know a better solution I'd thank you if you'd let me know.
Please make a comment, thanks for reading!
Installing a gem fork from Github source
Usually, installing a gem is as easy as issuing:
gem install gem_name
but, what if you want to install a fork of a gem?
As you may know Github no longer hosts gems, so doing the following won't work:
$ sudo gem install technoweenie-grit --source http://gems.github.com
NOTE: Actually it'd work if the gem you're trying to install is in this list: http://gems.github.com/list.html
Disecting the "Download Source" button
Let's suppose we want to install the Techno Weenie's fork of Grit from Github:
Main repo => http://github.com/mojombo/grit
Techno Weenie's fork => http://github.com/technoweenie/grit
Github has a "Download Source" button, if you click it you'll be presented with two big images (say buttons): "ZIP" and "TAR", clicking these buttons will start downloading the code of the master branch in the selected format; below those buttons you'll find the list of tags of the repository, you'll be able to click one of the tags and again you'll be presented with "ZIP" and "TAR" to download the source of such tag.
How does this works?
This is how the URL is built:
http://github.com/USER/REPOSITORY/FORMAT/BRANCH_OR_TAG
"ZIP" => http://github.com/technoweenie/grit/zipball/master
"TAR" => http://github.com/technoweenie/grit/tarball/master
said this:
$ wget http://github.com/technoweenie/grit/zipball/master $ unzip technoweenie-grit-v2.0.0-12-g0bd0c5f.zip $ cd technoweenie-grit-0bd0c5f
Installing the gem
Gems source code has a special file called gem_name.gemspec, this is like the DNA of the gem and it's used to build it:
$ gem build grit.gemspec
Issuing this command will generate a gem_name-version.gem file which is the gem itself, let's install it:
$ sudo gem install grit-2.0.0.gem
Some projects doesn't have a .gemspec file but rake tasks, in that case you just need to do:
$ rake build $ rake install
If any of these methods work, you'd have to look at the Rakefile for tasks to generate the .gemspec file.
...and we're done!
NOTE: 'gem build' will not take in consideration special and external dependencies the gem might require, so you must take care of the dependencies manually. Check in the code all the 'require' lines to see dependencies.
Hope it helps.
Does anyone knows an easier method?