Like most programmers I have a workflow that allows me to type code at one end, and a seamless, bugfree application will pop out of the other ;). Some part of the workflow invariably involves the use of Source Control Software, which at a minimum allows me to store away a versioned list of work so if something untoward should happen to my workstation my code and resources are at least retrievable in one form or another.
Over the years I have used many Source Control systems, the most recent CVS/SVN, and have issues with most of them (a subject of another blog…) but in 2010 a tool forced its way into my workflow… Mercurial (Hg). This is part one of my adventure in getting this running on windows.
What is Hg?
Its a source control system, but not as we know it. You don’t have a single central repo unless you explicitly create one with a workflow. Each user can clone a repo do work on a repo and let other users clone their new repo and commit changes at any level, gradually merging changes back into the main “branch” as needed. This allows users to create their own clone of the “main” repo (which can be backed up separately) without affecting other users… other users can get and work on this repo, and when ready the code will be promoted back into the main repo (try doing that with branches in CVS and I think you will prolly end up crying at some stage…)
For more information have a look at the use case workflows and the wiki that covers a basic explanation of it.
What Do I Need To Try This Out
In this first part I’ve got Hg running on a basic webserver. Using these apps you can set up pushes/pulls to a repo and test a basic setup of Hg that is visible to multiple users. The next step is to get a security model and pulling/pushing from SVN/CVS which I’ll cover in another post. To Try this out you need the following:
- The latest version of mercurial, I’m using 1.4.2 without Tortoise… showing the command line some love :).http://mercurial.selenic.com/wiki/Download?action=show&redirect=BinaryPackages#Windows.
- The version of Python that this version of Hg is built against. In this case its python 2.5. http://www.python.org/download/releases/2.5.4/
- Perl to handle cgi. I’m loving Strawberry perl at the moment, you can get it here: http://strawberryperl.com/
- A web server of some sort. I’ve gone for the free server Abyss, but it works on Apache also.
How To… Install
- DL and install Mercurial. It is pretty self explanatory, once installed open a command prompt, type “Hg <enter>” and you’re on your way.
- DL and install Python 2.5.4. Again pretty easy, DL, run the exe and you’re away.
- You can create a new repo by creating a directory on your machine, cd’ing into the dir in a command prompt and typing the line below… it’s as simple as that, and anything below the directory can now be added to the repo.
- I want to be able to share the repo with other people outside in the real world. There is some documentation that explains how to do it, have a look at it here:
- To publish the repo I’ve decided to use the HgWebDir method as it allows secure push/pull, user authentication and multiple repos under a single directory. To allow this I’m using the Abyss webserver, although you can use Apache. DL and install.
- To create my first checkin/commit you need to create a new user, so look in the Mercurial.ini file under your Hg installation and add a username in the [ui] section. You should be able to find the file here if you’re using the standard install path: C:\Program Files\Mercurial\Mercurial.ini. Add the following snippet to add a new user “Bob A”
username = Bob A <email@example.com>
- For the test I created a new projects directory, c:\temp\MercurialTest\Project. From the command line:
cd /d c:\temp
- Create some test files to add to the repo. From the command line:
echo thisisastring > Test1.txt
echo thisisastringalso > Test2.txt
- Add the files to the repo. Calling this will add all new files in this directory and recursively in the directories below that are yet to be added. From the command line:
- Commit the files and notepad will pop up, insert your change comment, save and exit notepad and the commit will occur. From the command line:
- So you have Mercurial working, now to set up your webserver. Install Strawberry Perl and Abyss server.
- Perl/Python will need access to the raw libs that were used to build Mercurial, which Hg contains in a zip in the Mercurial installation directory. Unzip the c:\program files\Mercurial\Libraries.zip file to a new directory c:\Program Files\Mercurial\lib.
- We want to be able to browse to our Hg repos over the web, so we’ll need some form of gateway to them, and we can use hgwebdir.cgi for this. Unfortunately this doesn’t come in the Windows installation pack, so you’re going to have to get this another way. The simplest method is to clone the hg repo and get it from there. Open a command prompt, go to the repo root directory we created earlier (C:\temp\MercurialTest ) and run the commands below:
hg clone http://selenic.com/repo/hg
- You can now copy the cgi file from here to your Hg installation dir for later use.
cp C:\temp\MercurialTest\Mercurial\hg\hgwebdir.cgi C:\Program Files\Mercurial
- You need to modify the first line of hgwebdir.cgi to point to your Python exe as shown below.
# An example CGI script to export multiple hgweb repos, edit as necessary
- Modify hgwebdir.cgi to point to the lib directory we created earlier:
# adjust python path if not a system-wide install:
sys.path.insert(0, “c:/Program Files/Mercurial/lib”)
- Move the Templates folder from the Mercurial installation to the libs directory also.
- Create an hgweb.config file in the Mercurial installation directory containing the snippet below. This will set up our root code repo directory as a virtual directory so it can be accessed using the CodeRepo key across the web:
CodeRepo = C:\temp\MercurialTest
- We need to configure the Abyss webserver so we can browse and update the Hg repo. Since we installed Abyss earlier it should be running on your machine at the moment, so in your web-browser de-jour open a new page and browse to http://127.0.0.1:9999 which should show a page look remarkably like the Abyss configuration screen below:
- For your webserver go to Abyss Go to Configure > Scripting Parameters > Script Paths > Add which should show you a list of blank interpreters and virtual paths as Abyss is a new installation.
- Add a new CGI/ISAPI interpreter, point it to c:\strawberry\perl\bin\perl510.dll and set the file extensions supported to cgi and pl. It should have a line as below once you’ve added that data:
CGI/ISAPI c:\strawberry\perl\bin\perl510.dll cgi pl
- Add a new virtual path on the same page. We’re going to create a directory on the computer which will point to the same path later.
- We want to create a new directory structure which will contain our cgi and html docs. Create a new directory for this (c:\temp\web as a test) and we will configure abyss to point to this. Go to the root Abyss configuration screen, then go to Configure > General > Documents Path and set it to c:\temp\web.
- Add an Index.html file with the following snippet for the moment as a test to your c:\temp\web directory:
This is a test.
- Set your browser to 127.0.0.1 you should see a page saying “This is a test”.
- Create a sub directory under c:\temp\web called cgi-bin and copy the hgwebdir.cgi and hgweb.config files from your Hg installation directory to it.
- Browse to http://127.0.0.1/cgi-bin/hgwebdir.cgi as a test and you should see a screen resembling below, your repos are now officially online.
Before we go any further its probably best to test that you can access the repos both on the same machine and off machine to ensure that everything is working as expected.
To test on the webserved machine:
- Create a directory in your MercurialTest directory to contain the clone:
- Open a command prompt, cd to the directory and clone ProjectA
- Now when you look in the ProjectACopy you should see the files we checked in earlier and if you set your browser to the cgi file as before you should see 3 repos.
To test on another machine:
- Create a working directory on your machine. Clone using the URL of the webserved machine:
- Now when you look at the hgwebdir.cgi you should be able to see a new cloned version.
Backing Up A Repo
The simplest method I can see is to clone a repo/push changes to a repo, and save the repo to backup/zip up the directory structure and hive off to disk. If something goes wrong you clone the backed-up repo and voila :)…
A few things to look into:
- At the moment all the world can see and interact with your repo, which we probably don’t want… so we need to look at locking down the repos to known users, and using SSH for authentication and pushing/pulling to your repos.
- The server will support pull by default, but not push, we need to turn that on.
- Hg can push/pull to CVS and SVN. Wouldn’t it be nice to have this working.
- Setting up an automated backup.