Working with Subversion

Note: This post is over a year old. You may want to check later in this blog to see if there is new information.

Okay, so we’ve installed subversion and covered the basics. Let’s go ahead and make our first actual repository on a remote server and check out a local working copy, as well as look at a few possible workflows to see what will work best for each of us.

The Remote Repository

First log in to your remote server. You should have set up a password free ssh connection and have Subversion installed on the server. Make sure svn is in your path as we talked about yesterday (verify by typing “svn —version” and getting a response). Lets begin by making a directory to hold our repositories. I put mine in /var but you can choose to put yours wherever makes sense (and you have write access).

cd /var
mkdir repos

And then create our first repository. Yours will obviously be named based on the website you’re importing, so replace the name with something that makes sense for you.

svnadmin create portfolio

Now we’re going to import the website into the repository. This does not turn the website into a working copy or affect it in any way. It just adds the files to the repository. You’ll have to make a checkout before you’re actually editing anything under revision control.

svn import /var/www/vhosts/circlesixdesign.com/httpdocs file:///var/repos/portfolio/trunk -m "initial import"

The “trunk” ending on the repository name gives us the beginnings of a workflow that can incorporate trunks and branches. Branches are like subprojects where changes and tests can occur before they’re merged in with the main trunk. You now have a working repository which we can check out on our local machine. Assuming you have your password-less svn set up, we can log out of our remote machine and switch to a directory on our local machine. Before we copy the whole site, though, let’s look at the workflow.

Workflows

We can have a simple workflow:

The live website is a working copy, the local working copy is set up as a test server. When you make changes to the local copy you can test them before committing them. Once they are committed, they go live.

We can add a layer to that workflow:

The testing server and local copies are working copies (checkouts) and the live website is an export. The same methodology as above applies, but changes go to a testing server first and are then exported from the repository to the production (live) server. This allows for multi-platform testing prior to deployment and prevents the .svn directories from being created in the live copy.

Further, we can add branches to that workflow to have experimental and stable checkouts. We can also have multiple people with multiple checkouts and different branches working together on one project, with Subversion handling conflicts that arise.

Thomas Aylott suggests a few more workflows

Essentially, what we’re going to do today is set up the simplest scenario. I don’t want this to get overly complex, but I encourage you to explore the available resources. Our local checkout is going to be of the trunk that we created. We’re going to assume you can create a local database and create a local test environment around the checkout, so all we really need to be able to do is get the full copy of the website into a place where our local server can find it. In my case, that’s in the ~/Sites directory where I have MAMP set to look.

The Local Checkout

We’re going to use the abbreviation for checkout (co) and the svn+ssh protocol to access the repository. With your public and private keys in place, this should be able to connect without intervention.

So I’m just going to type:

cd ~/Sites
svn co svn+ssh://yourusername@yourserver.com/var/repos/portfolio/trunk portfolio

This is going to copy the entire repository to a directory called portfolio for me to work with. I can then load up Headdress and add the directory to MAMP, and edit my config files to point to a database. I generally log into the production database using phpMyAdmin and do a dump of the whole database and then import it into my local phpMyAdmin, keeping the database name the same. All I generally have to do then is add a port to the database server in the config file (i.e. localhost:8889).

Ignorance is (not) Bliss

We don’t want that config file checked back in, though. This is one of those spots where things get tricky. If we just do a commit right now, it will modify the config in the repository and eventually overwrite the config on the production server. We need to ignore that file. So here’s what we’re going to do. Again, if there’s a better way, I’m eager to hear it.

  • Copy the config file somewhere safe. Like your desktop.
  • Type: svn rm wp-config.php (or whatever config file you need to ignore)
  • Type: svn propset svn:ingore ‘wp-config.php’ .
  • The trailing period is important, and those should be straight single quotes, no matter what Wordpress tells you.
  • Copy the config file back into the directory and commit the changes

You should now be able to make changes to the config file without them showing up when you type “svn status”. However, when you do a checkout of the repository now, the config file will not be included. If you eventually convert your production server to a working copy, you’ll absolutely have to remember to copy the config file over. The best way I’ve found to do this is to create a checkout called working parallel to httpdocs (or whatever your server calls the web directory) and do a full checkout there. Then copy over the pieces that you’ve ignored but still need. Then type: “mv httpdocs httpdocs.old;mv working httpdocs” and switch the two directories out seamlessly.

If you follow this path and create a working copy for your live server, we’ll need to keep Apache from descending into all of the .svn folders. This can be done by editing your httpd.conf and adding:

# Disallow browsing of Subversion working copy administrative dirs.
<directorymatch "^/.*/.svn/">
    Order deny,allow
    Deny from all
</directorymatch>

Tomorrow we’re going to run through making a few changes and testing them, committing them and updating the remote server before we get into TextMate and the graphical clients. I’ll also show you how to have a remote checkout automatically updated when you commit local changes.

» » » » » » » »
  1. 3stripe 07.22.07 / 8am

    Great article!

    I’ve just started learning Subversion and all the how-to’s on your blog have been a massive help.

    Cheers, 3stripe

  2. Ray 10.31.07 / 2pm

    To deal with the local vs production config problem, I create a parallel branch to hold my local versions of config files, then do a svn copy of the config files into the branch, svn switch my working copy to the branched version, then do my local changes and commit. This way, when you commit, it commits to the branch, not the trunk, so the trunk version stays a good copy of the production setup. If you need to make changes to both your local and production config files, make them and do a svn merge to keep them in sync. Does that make any sense?

  3. Daniel 03.03.08 / 1am

    Appreciate the article!

    I got the following error when I followed your instructions:

    bash: line 1: svnserve: command not found
    svn: Connection closed unexpectedly

    What solved it was creating a file called .bashrc in the home directory of my test server and adding the following line:

    PATH=$PATH:/usr/local/bin

    Good luck!

Have your say

XHTML: You can use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <code> <em> <i> <strike> <strong>




Safari hates me