Using Subversion and Rails
I don't know why it took so long. Years actually. I'm not talking about the technical install. I'm talking about finally getting around to committing to use revision control tools for my own projects. Yes, I've used clients here and there for getting stuff from other (open source) projects and playing committer at times. This week I buckled down and setup my own (localhost) server and procedures for my development. My platform is OSX on an iMac.
The first decision was which product to use. Xaraya uses Monotone , so I've become familiar with it. Monotone has some awesome features (like peer to peer sync, crypto, integrated testing); yet some things confuse me, I won't go into it now (from their manual: "Please be aware that monotone is a slightly unorthodox version control tool, and many of its concepts are similar — but subtly or significantly different — from concepts with similar names in other version control tools.") Yeah, I agree.
It seems most other open source projects are using Subversion , including the entire Rails community. Subversion may be dumber than Monotone, but it feels more comfortable to me.
For hosting, I took a serious look at Google Code Hosting which runs subversion. It's designed for FOSS (free and open source) projects so while you can assign "members" with check in privileges, anyone in the world can pull from the repository. Unless they change their policy and let me limit the access, it won't work for my purposes. So for now I'll use localhost, and later, get it running on my internet server.
Actually I already had subversion (svn) installed, from when I installed Rails. But if you don't, do this (using macPorts):
$ sudo port install subversion +tools
It's important to understand the concepts, workflow, as well as the specific commands for svn. The O'Reilly book "Version Control with Subversion " is available free in PDF format. Already familiar with the concepts of revision control, I jumped to the Appendix A High Speed Tutorial, then skimmed through the rest of the book.
For using svn with Rails, there's two great articles. The posting on Maniacal Rage (by Garrett) is pretty straightforward. I followed the text but didn't implement it directly. Then I went on to Subversion Primer for Rails Projects (by Francois) which seems to the definitive guide. Both articles are about a year old.
Next, I looked around for a GUI front end. Oh, sure, real men only use the command line. Well, I'll bet you real men, like me, occasionally open up a Finder (or File Explorer) and click around to find, move, rename, organize your files, even though you can do it all on the command line too, right? I see revision control just a fancier file system (in fact, when the heck will it be integrated into the OS anyway?!)
What I found were two choices on the mac:
svnX is free and open source. Zig is proprietary and has a license fee for commercial use but free for personal use. I found Zig to be a bit easier and more intuitive to use, so I went with that. (Zig's visual diff viewer rocks!) (But if I had to, svnX would do just as well.)
I won't go into a big long explanation of how and what to do to get your rails project into svn, since Francois (and Garrett) have already done that. Rather, here's Francois' shell script, which I've slightly modified:
Usage: rails-svn PROJECT
In summary, the script does this
- Creates a repository for PROJECT
- Creates initial trunk/, tags/ and branches/ directories
- If project doesn't exist, runs rails and creates a PROJECT_development database
- Add all project files to the repos
- Ignore log/*, tmp/*, doc/*doc, and config/database.yml
- Creates a database.yml.sample instead
- Removes public/index.html (it just gets in the way)
The changes I made include
- Let you setup an existing rails project, not just a new one
- Creates the PROJECT_development database with mysqladmin
- Does not ignore db/schema.rb (per DHH's comment on Francois' site)
- Commented out the Rails Edge external
Note, Francois' loud disclaimer applies here too: NO IMPLIED WARRANTY. This script might destroy twenty years worth of work, and I cannot be held responsible. Heh.
Start a Working Project
OK, assuming you have the script in your path, its free sailing from here. I keep my rails projects in ~/rails and my repos in ~/svn. Source code is maintained in the trunk directory of the repos.
$ cd ~/rails
$ rails-svn myproject
If myproject doesn't exist (in ~/rals/myproject), the script runs rails to start an empty one, and adds the files to svn. If myproject already exists, it s files will be added to svn as is.
Fire up zigversion and choose "import working copy" for the newproject directory. Tada!
Working on a Project
When you edit a file, it will show as modified in the zig window. When you want to commit your changes, you can check in the whole tree-- click on "/" and Check In, or on the command line
$ cd ~/rails/myproject
$ svn commit --message="reason for these updates"
or do it a file or subdir at a time.
When generating rails files, use the --svn command to automatically add them to svn. For example,
$ script/generate scaffold_resource --svn rabbit name:string created_on:date
$ rake db:migrate
You might need to refresh the zig window.
When you need to add generated files and/or if you forget ot use --svn, run add manually,
$ svn add --force .
Committing Your Environment
At a minimum, you may want to freeze your rails version and keep it in the repos
$ rake rails:freeze:gems
$ svn add --force vendor/rails
$ svn commit --message="freeze rails"
Francois also includes some great detail on how to manage the Rails version (using svn:externals), gems, and plugins, so you can ensure your production site is configured the same as the development one. Here's a distillation of his instructions:
To link to rails repos:
Replace branch with your preference for tags, trunk, or stable copy you want.
$ svn propset svn:externals "rails http://dev.rubyonrails.org/svn/rails/branch/1-2-stable" vendor
$ svn update vendor
$ yes | rails .
$ svn commit --message="set svn:externals on vendor/ for Rails"
To repos your gems:
Make a copy in your vendor directory and check it in. Preserve license files. Add a svn property to help remember what this is.
$ cd vendor
$ gem unpack gemname
$ cp -Rf gemname-n.n.n/lib/* .
$ cp -Rf gemname-n.n.n/MIT-LICENSE LICENSE-gemname
$ cp -Rf gemname-n.n.n/README README-gemname
$ svn add aaaa bbbb cccc dddd.rb LICENSE-gemname README-gemname
$ svn propset version "n.n.n (Gem)" gemname.rb
$ rm -Rf gemname-n.n.n
$ cd ..
$ svn commit --message="Unpack Gemname n.n.n into vendor/"
When the gem upgrades, repeat but notice which files changed, added, removed.
To repos your plugins:
$ svn propset svn:externals "plugname http://plugin/url/tags/rel_0-3-1/" vendor/plugins
$ svn update vendor/plugins
$ svn commit --message="Added Plugname plugin"
Deployment to a Web Server
See the post, "Deploying my first rails site" for deploying from a local SVN to a production server using Capistrano.