How I learned to stop being a Cowboy and Love the SVN
Cowboy, you been barking up the wrong tree. If you’re editing your site, and/or your clients site live. Well then buddy your doing it wrong. Don’t get defensive, and don’t be ashamed. Till recently I too was a gun slinging, rope totting Cowboy. I always knew there was a better way to do things, I just didn’t quite understand how. Then at WordCamp NZ 2011 John Ford from automattic mentioned in passing ‘.. that if the hacked site is running on SVN you can just do an svn st and svn diff to see the hacked files..’ Which made me raise an eyebrow. I mean, I’ve used SVN for Plugin development, I’m no self-proclaimed expert but I know enough to run a Plugin on the WordPress Plugin repository but an entire site? HOW? wouldn’t that get messy if you had Plugins from one repository themes from another? How is this possible? I kidnapped John after the WordCamp was over so he could teach me his trick, and now I feel less like a Cowboy and more like a hippy. Why? ‘Cause I LOVE the SVN
Ok so what are we planning on achieving here?
Basically we want to have the ability to make changes, and test them on our local computer (or staging site) before pushing those changes to the live site.
I know in a real deployment we would have development, staging, live but for this tutorial I am only going to run through development and live. Why? Cause Im a lazy Hippy not a full blown developer.
So while we were going through the processes of settings things up I came across a this resource that might help you out as well:
- http://ottopress.com/2011/creating-a-wordpress-site-using-svn/
Before I start my ramblings I assume you know the basics of SVN, if not check out these resources before hand:
- http://codex.wordpress.org/Using_Subversion
- http://codex.wordpress.org/Installing/Updating_WordPress_with_Subversion
- http://svnbook.red-bean.com/
What you need:
- A sense of humor
- An Empty SVN Repository – (in this tutorial I will call this repository http://svn.example.com/site1)
- LAMP, XAMP or MAMP
- Some basic Terminal knowledge
1. Create your Work Environment
Create a folder ‘site1′ to hold the site (usually in your htdocs folder) navigate your way into it using terminal and Checkout a fresh, empty copy of your SVN repository:
svn co http://svn.example.com/site1 .
This should checkout a copy of the repository which should just a .svn folder and no other files.
2. Setup your Externals
This was the new and fun part, svn externals. we are going to include a copy of WordPress into a new folder called wp. In terminal navigate into your site1 folder and type in this command:
svn propedit svn:externals .
This will open up a text editor like vim, in here hit ‘i’ for insert. Then type :
wp http://core.svn.wordpress.org/tags/3.1/
Then hit ‘esc :wq’ and hit enter, you should see a message like “Set new value for property ‘svn:externals’ on ‘.’”
3. Update your Working Copy
With your new external in place type svn up to start downloading WordPress!
4. Setting up your wp-content folder
From the site1 folder in terminal type:
svn mkdir wp-content
svn mkdir wp-content/plugins
svn mkdir wp-content/uploads
svn mkdir wp-content/themes
Now instead of copying the akismet plugin and twentyten theme from wp/wp-content to wp-content we will add them as symbolic links (we will also do this with the index.php files which live in each folder, inside the wp-content folder in terminal type:
ln -s ../wp/wp-content/index.php index.php
Then in the themes folder:
ln -s ../../wp/wp-content/themes/index.php index.php
ln -s ../../wp/wp-content/themes/twentyten twentyten
Then in the plugins folder:
ln -s ../../wp/wp-content/plugins/index.php index.php
ln -s ../../wp/wp-content/plugins/akismet akismet
If you navigate into the site1 folder and do an svn st you will see all the symbolic links we just made have not been added to the repository yet. so we will have to go ahead and do that:
svn add wp-content/index.php
svn add wp-content/plugins/*
svn add wp-content/themes/*
5. Setting up your external Plugins
Thats great but we want a few other bits and pieces too, for example, I do a lot of work on the WP e-Commerce Plugin so I’d like to run the latest and greatest of that (or any other Plugin I run). Navigate to the plugins directory in terminal and type:
svn propedit svn:externals .
This will open up a text editor like vim, in here hit ‘i’ for insert. Then type :
wp-e-commerce http://svn.wp-plugins.org/wp-e-commerce/branches/3.8-development
Then hit ‘esc :wq’ and hit enter, you should see a message like “Set new value for property ‘svn:externals’ on ‘.’” Now all you need to do is type ‘svn up’ in terminal and wp-e-commerce plugin directory will be populated with the latest and greatest
6. Setup your .htaccess
So this part was awfully tricky for me, I’m no expert at .htaccess rules, so I just copied this part from the above resource. Essentially add a new .htaccess file to your site1 folder and add this to the file:
Options -Indexes
RedirectMatch 404 /.svn.*$
RewriteEngine on
RewriteCond %{REQUEST_URI} !^/site1/wp/
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ /site1/wp/$1
RewriteRule ^(/)?$ wp/index.php [L]
Once you have done that, make sure you add it to the repository, in terminal:
svn add .htaccess
7. Setup your config file
With the .htaccess file rocking, you should now be able to navigate to site1 using a web browser and complete the normal WordPress Install which setups your DB and wp-config files. Once that has been done, I strongly suggest you
a. Change the permissions on your .htaccess file so WordPress can’t overwrite it.
b. Add these lines to your wp-config.php file so your install uses the correct wp-content folder:
define( 'WP_HOME', 'http://sites/site1' );
define('WP_CONTENT_DIR', dirname(__FILE__) . '/wp-content');
define('WP_CONTENT_URL', WP_HOME.'/wp-content');
8. Make your config file not part of the SVN repository
Ok, so having your wp-config file in the repository is a no-no. If someone accidentally got into your SVN Repo, or hacked in, then they will have your username, password and DB details.. which is a scary thought. So what we do here is make SVN ignore the wp-config.php file, so it doesn’t get added to the repo. In terminal navigate to site1 and type:
svn propedit svn:ignore .
This will open up a text editor like vim, in here hit ‘i’ for insert. Then type :
wp-config.php
Then hit ‘esc :wq’ and hit enter, you should see a message like “Set new value for property ‘svn:ignore’ on ‘.’”
9. Check in your new repo
With everything said and done, head over to site1 in terminal and type:
svn ci -m 'Checking in my new Website while learning how not to be a cowboy'
That’s that. We now have a repo for our new website, and can work on any computer without having to deal with the live site.. Things to consider:
- Data. What we have comitted had nothing to do with live data, so for instance if you are trying to do this with a currently active site I would import the DB and change the wp-config file once we have completed the steps above.
- Uploads Folder. now I haven’t heard any good / bad way to do this, and personally I log in to my live server every now and then and check in all my files in the uploads directory. That way I can download the latest DB and the files can associate after an svn up on my local working directory.
If you have any tips, advice, or found this post useful please leave a comment. I’m interested in extending this deployment strategy and learning how other people stopped being cowboys.
Note: If you are trying to setup propedits and are getting an error please try this in terminal:
vi ~/.bash_profile
This will open up a text editor like vim, in here hit ‘i’ for insert. Then type :
export EDITOR=vim
export SVN_EDITOR=vim
Then hit ‘esc :wq’ and hit enter, Quit terminal and try again, you should be able to get through successfully.
Till Next time,
Peace man!
2 Responses to “How I learned to stop being a Cowboy and Love the SVN”
Leave a Reply
Great article. I’m considering doing something similar, but not having the DB on the SVN (and thus allowing me to go back in time not just in terms of the files but the state of DB as well) is worrying me.
I’m already doing DB dumps with mysqldbdump( mysqldump –add-drop-table — add-locks=FALSE -u user -p pass -h host database > dump.sql) so I’m wondering that just adding that to the subversion repository could work fine. Ideally this could be run daily with a cron job and at the end of every day you’d get a commit to your repos with the DB state of that day.
In case your site ever got hacked you’d just have to switch back N days.

Great article. I’m considering doing something similar, but not having the DB on the SVN (and thus allowing me to go back in time not just in terms of the files but the state of DB as well) is worrying me.
I’m already doing DB dumps with mysqldbdump( mysqldump –add-drop-table — add-locks=FALSE -u user -p pass -h host database > dump.sql) so I’m wondering that just adding that to the subversion repository could work fine. Ideally this could be run daily with a cron job and at the end of every day you’d get a commit to your repos with the DB state of that day.
In case your site ever got hacked you’d just have to switch back N days.
hmmm id think carefully about storing your db dump in the svn repo, just because you’d have all your users and passwords etc,,, if you come up with a solution please do come back and share your findings
best
jeff