Git and gitolite nirvana

January 21, 2011 3 Comments by Richard

Having recently begun switching all of my projects to use git for source control, I have been using gitosis on my server and have been pretty happy with it. However, the one thing that kinda annoyed me was that every time I wanted to create a new repository, I had to go add it to the config file.  I found myself making up excuses to just use a raw ssh to my server at home.  This, of course, was also a bit of a pain since I had to go set up a raw repository each time I wanted to do it…

Enter gitolite

Gitolite has a really cool feature that I make heavy use of called “wildcard repositories”. The way I use it, this lets me set up a group of users (@wildcardusers) that can create whatever arbitrary repositories they want in a subdirectory of the same name as their username.

In the gitolite.conf file:

@wildcard_users = richard jarom ben
 
repo    CREATOR/.*
    C     = @wildcard_users
    CRW+D = CREATOR
    RW    = WRITERS
    R     = READERS

Voila! I can now push to any repo looking like [email protected]_server.net:richard/my_repo.git

Setting the default remote HEAD

Ben and I happily used this for the better part of a day before we ran into our first disappointing snag. Ben is a huge fan (and I as well to a lesser extent) of git-flow, but with the layout we normally use with git-flow the default repository should be named “develop” instead of “master”.  Well, no problem, right?  A quick git checkout -b develop and we have a develop branch, then git branch -D master and the master branch is gone.  git push origin :master removes it from the gitolite server, and we’re ready to roll!

Oops! When we clone the repository, it clones okay but gives us an error at the end that it can’t find the HEAD ref. This is aparently a normal git configuration thing that has to be done on the server, but users who can create wildcard repositories shouldn’t need shell access on the box!

Fortunately, gitolite supports Admin Defined Commands (ADCs). They are suprisingly easy to use if you know a bit of shell script programming (or python, as I’ll explain later). As of a commit last night, there is now a set-head ADC in the contrib directory in the main repo.

ssh [email protected]_server.net set-head richard/my_repo.git refs/heads/develop

Simple as that, the HEAD is changed!  Note that ADCs have to be enabled and configured before you can use them.

Giving other users access to your repo

As you probably gathered earlier, this server is used by a small group of people who often work on projects together. Sometimes we need to give someone else access to our repository.  We might also want to just give access to anyone through the git:// protocol (which gitolite supports when configured correctly using the daemon user).

You can do this using the setperms and getperms built-in ADC.  However, these are a little inflexible for my tastes, and I had a few minutes, so I wrote a quick python helper class for writing ADCs and threw together the perms ADC, which is also in the main repo now.

You can run the command and see the help for yourself, but here is a quick example of what you can do:

richard@machine:~ $ ssh git@my_server.net perms
Usage: perms <command> <repository> <args>
             list <repository> [TYPE]
             clear <repository>
             add <repository> <TYPE> [user and group list]
             set <repository> <TYPE> [user and group list]
             remove <repository> <TYPE> [user and group list]
 
richard@machine:~ $ ssh git@my_server.net perms list richard/test.git
WRITERS:
    fred
READERS:
    ben
    jarom
richard@machine:~ $ ssh git@my_server.net perms add richard/test.git WRITERS billy
WRITERS:
    fred
    billy
richard@machine:~ $ ssh git@my_server.net perms add richard/test.git READERS joe
READERS:
    ben
    jarom
    joe
richard@machine:~ $ ssh git@my_server.net perms remove richard/test.git READERS jarom
READERS:
    ben
    joe
richard@machine:~ $ ssh git@my_server.net perms set richard/test.git READERS ben jarom
READERS:
    ben
    jarom
richard@machine:~ $ ssh git@my_server.net perms list richard/test.git
WRITERS:
    fred
    billy
READERS:
    ben
    jarom