“is bemused/awed by how fast svn became a legacy technology in ruby community/developers” Dr. Nic recently said on Twitter. It is true. Greatly aided by Geoffrey Grosenbach’s screencast on git, I myself is starting to feel comfortable enough with git to start abandoning subversion altogether.
Github is great, but there is really no reason to pay for private git repositories unless you need the added functionality. I have a Dreamhost account that I am happy with, so why not use that for my private git repos? It is easy to do through SSH, now that git is installed on all Dreamhost servers, but it is not that easy, so I thought I’d better document it here for my own future reference.
(This stuff is tested on Mac OSX, and should work fine for *nix users. Windows users will have to do some workarounds, but can use this as a reference point.)
Create and add your public key (optional)
If you are used to use SSH access with Dreamhost, you probably already have this step setup, but if you don’t, this will help you avoid having to type your password everyone you connect through SSH, which will be every time you pull and push to and from the git repo on Dreamhost.
If haven’t done any SSH at all, you will probably need to generate a public/private set of RSA keys:
ssh-keygen -t rsa
Then you’ll need to to add your public key to your server (thanks to Dave the Wave for this trick):
cat .ssh/id_rsa.pub | ssh email@example.com 'cat >> .ssh/authorized_keys'
And with that, you can SSH to the server without typing your password, which is almost a must when doing git over SSH.
dreamgit shell script
Toolman Tim explains very well how to setup a remote git repository over SSH, but it is easy to mess things up, and I’m planning on doing all my stuff in git from now on – so an automated script to suit my needs is essential.
I am not an expert in either git or shell scripting, so this script can probably be optimized quite a bit – in fact I am more than willing to update it if I get any comments from the real experts out there. But this script works for me:
DREAMGIT_DOMAINfirstname.lastname@example.org ssh $DREAMGIT_DOMAIN 'mkdir -p ~/git/'$1'.git && cd ~/git/'$1'.git && git --bare init' mkdir $1 cd $1 git init git remote add origin ssh://$DREAMGIT_DOMAIN/~/git/$1.git touch .gitignore git add . git commit -m 'Created new repo' git push origin master echo " [branch "master"] remote = origin merge = refs/heads/master" >>.git/config echo "Your new git repo '$1' is ready and initialized at $DREAMGIT_DOMAIN/~/git/$1.git"
Put the above code into a file you place in a directory in your
PATH. Remember to change
email@example.com to your real Dreamhost SSH user and domain. I’ve selected to name the command
dreamgit and put it in
/usr/local/bin like this:
sudo mate /usr/local/bin/dreamgit
Paste the code in and save the file. Make your new command executable:
sudo chmod a+x /usr/local/bin/dreamgit
You now have a new command –
dreamgit – that you can invoke in any directory on your local machine. You call it with a single argument – the name of your project – like this:
dreamgit test05 Initialized empty Git repository in /home/.char/cfp/git/test05.git/ Initialized empty Git repository in .git/ Created initial commit f4fbb71: Created new repo 0 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 .gitignore Counting objects: 3, done. Writing objects: 100% (3/3), 220 bytes, done. Total 3 (delta 0), reused 0 (delta 0) To ssh://firstname.lastname@example.org/~/git/test05.git * [new branch] master -> master Your new git repo 'test05' is ready and initialized at email@example.com/~/git/test05.git
As it says – you now have a fresh repository ready for action, pulling and pushing to your remote repo at Dreamhost.
How it works
On the server, it creates a folder named
git in your home directory – if it doesn’t already exists – and creates a directory named
project_name.git in it. It then initializes a bare git repo in that directory, meaning that the repo will hold the git database only, and is not used for doing actual work in.
On your local machine it creates a directory with the project name, initializes a git repo in it, adds an commit an empty
.gitignore file to it, and pushes that to the remote repo on your server. Finally it sets up the remote repo to be the default push and pull location for the master branch the local repository. This way, we only have to type
git push and
git pull without specifying which remote repo and branch we want to interact with.