About Books Credits Photos Software Rumblings Travelling Home
rrt_ruby side-effects

I just finished with the first public release for rrt_ruby and apart from patting myself in the back there are a few things I learned that I’d like to jot down.

My development environment revolves around subversion. I never used cvs in any meaningful way and after working a year with subversion I have no intention of relinquishing it’s luxuries for either cvs, nor clearcase, nor even perforce whose jobs I like so much.

So the obligatory use of cvs with RubyForge is a blow and I needed to work around it.

The solution is to keep working in subversion and periodically copy everything over the cvs repository and add/submit. This works ofcourse because I’m the only developer in the project, but I have been doing something similar with the clearcase repositories at work and a couple of supporting Ruby scripts for the last year or so, so the workaround adapts itself to multiple developers.

What’s new this time is that the whole copy procedure, as well as the publishing of the HTML for rrt-ruby.rubyforge.org is done automatically with a rakefile. If you’re using Ruby and don’t know what Rake is, take the time to learn about it, it makes life significantly easier.

The first problem I faced with Rake was to find a way to use the timestamping/comparing facilities of a file task without having to explicity name the tasks.

The important difference between a file task and a task is that a task is always executed, while a file task performs a comparison against it’s target file and does nothing when it needs do nothing.

Now, shifting through the documentation I found Martin Fowler’s “Using the Rake Build Language” which helped me overcome my initial confusion with the file tasks. I can define a task within a method, which allows me to do the following:


def to_target src,target_dir 

    tgt=File.join(target_dir,src)

    file tgt=>src do

        mkdir_p(File.dirname(tgt))

        cp(src,tgt) unless File.directory?(src)

    end

return tgt

end

So I am generating a file task with name tgt which depends on my source file. All one has to do is call the method for each file to copy and then add a dependency to the task that does the copying. This is very elegantly acomplished for i.e. the files for the site doing:


    SITE.each{|src| task :copy_to_cvs=>to_target(src,TARGETSITE)}

copy_to_cvs groups all copying file tasks together just by it’s declaration. Nice!

One

rake copy_to_cvs
later the whole repository tree is copied and ready for commit.

Nothing is copied when the destination file exists and is the same with the source file.

To take it a bit further, the same method is being used to publish the site using scp.

This time instead for the cvs repository the target is the ‘publish’ directory that is then copied using scp.

The disadvantage is that although we copy incrementally (from the repository to the ‘publish’ directory) we tranfer the whole site everytime.

One solution is to cache the names of the source files that are actually copied in the to_target method and then scp the sources instead of the copies.

I haven’t implemented it because I ‘m looking for a more clever solution than using a member variable but I definitely will – this is something important for the braveworld site, with it’s bandwitdth clogging media content.