Tom Purl’s Web Site

My ‘83 Datsun On The Side Of The Information Superhighway

Review: Agile Development With Rails, 3rd Edition

leave a comment »

Agile Web Development with Rails: A Pragmatic Guide (Pragmatic Programmers) Agile Web Development with Rails: A Pragmatic Guide by Dave Thomas

My rating: 4 of 5 stars
In general, this book does a fairly good job of helping you create a rails-based application. Part 3 includes some great in-depth information on the topics that are briefly discussed in Part 2.

I only have one real gripe about this book. It packs in lots of topics (e.g. db theory, AJAX, unit testing, security, deployment), but it doesn’t really tell you much about them. Therefore, if you have a problem, then good luck figuring it out using the content in the book.

A good example is the final chapter which covers deployment. The chapter devotes only a few small paragraphs to configuring Apache for passenger. To me, this section was completely useless unless you were already an expert with Apache configuration. I ended that chapter with a broken Apache server and no resources (from the book) to begin fixing it.

Another problem that I had with that chapter is that it really didn’t follow the pattern that the chapters in Part 2 used. In those chapters, the authors would should you how to do something relatively small, show you how to test it, and then provide some troubleshooting information if the task was particularly complex. The deployment chapter gave you a *very brief and generalized* tutorial in each section, and then just assumed that everything went perfectly. It didn’t show you how to test anything, and it didn’t help you troubleshoot any possible problems.

Don’t get me wrong. I know that no book will provide all of the information that I would ever need about a subject, and thank goodness for the internet in these situations. I was just hoping that all of the chapters in a book that I actually bought would provide better information than some person’s blog.

So in general, I guess I would have to say that this was a very good book with some bad chapters that were tacked-on at the end.

View all my reviews >>

Written by tpurl

February 3, 2010 at 2:29 pm

Walking With Rails 1 – Setup On Ubuntu

leave a comment »

Overview

One of my goals for 2010 is to gain a decent understanding of the Ruby On Rails framework.  I don’t think that this knowledge will directly help me with my current job (as a FileNet P8 administrator), but I do think that it will provide some good benefits.

First, learning about something that’s a little bit outside of your comfort zone can often help you with your day-to-day tasks.  For example, if you teach yourself the basics of Java development, then you will know how to read a stack trace.  Having this knowledge is very important if you want to administer software written in Java.

Also,  it’s just fun.  Creating something useful out of a few lines of text never ceases to amaze me.  Also, I find that learning new technical skills is good for your brain.

Finally, who knows what the future may bring?  It never hurts to know as much as you can about popular technologies in general when you work in IT.

So to get started, I purchased a copy of Agile Web Development with Rails, Third Edition from the Pragmatic Programmers’ web site.  This book seems to be one of the best for beginners, and I really love that you can buy DRM-free ebooks from the Pragmatic Programmers’ web site.

Installing Ubuntu Packages

So enough background information.  Here’s how I set up my system to get started with Rails development.  First, I installed all of the necessary software on my Ubuntu 9.10 machine that was  available as an Ubuntu package:

sudo apt-get install rails ruby-full rubygems rake mongrel git-core sqlite3

Here’s why I installed more than just the rails and ruby pacakges.  When you install Ruby from source on a Linux machine, you get a lot of software.  In addition to the Ruby runtime, you get fun tools like irb, rubygems, rdoc, ri, and rake.  However, when you install the ruby package on Ubuntu and Debian, you just get the Ruby runtime along with a a couple of libraries.  Since I’m lazy efficient guy, I decided to install the ruby-full package instead to save a few keystrokes.  Unfortunately, the ruby-full package still doesn’t include rake or rubygems, so I installed those manually.

Mongrel is a developer’s web server that is designed to work very well with Ruby on Rails development.  Since I am also impatient, I wanted a web server that would work a little faster than WEBrick.

Finally, I installed git because I wanted to share code between two different computers.  Git is a version control system that is very popular with Ruby developers, so I figured that I would use the most popular Ruby-related tools while I’m learning about Ruby.

Installing Software Without apt-get

Natrually, you can’t install everything that you need with apt-get.  For starters, the version of rails that is used in Agile Web Development with Rails, Third Edition is 2.2.2, so let’s install that using rubygems:

sudo gem install rails --version 2.2.2

This operation took a little while (~ 7 minutes) on my machine for some reason.

Note: For some reason, this bog

Next, I’m a Vim user, so I would like to see if the rails.vim plugin would help me at all.  There is an official Ubuntu package for this plugin called vim-rails, but when I try to install it using apt-get, I get the following error:

Some packages could not be installed. This may mean that you have
requested an impossible situation or if you are using the unstable
distribution that some required packages have not yet been created
or been moved out of Incoming.
The following information may help to resolve the situation:

The following packages have unmet dependencies:
vim-rails: Depends: vim-full but it is not installable
E: Broken packages

When I tried to install the vim-full package on my machine, I got this error:

Package vim-full is not available, but is referred to by another package.
This may mean that the package is missing, has been obsoleted, or
is only available from another source
E: Package vim-full has no installation candidate

Ok, so after all of that, let’s just install it the easy way:

(Download the latest version of rails.zip from the rails.vim download page)

$ cp rails.zip ~/.vim
$ cd ~/.vim
$ unzip rails.zip

Finally, open vim or gvim and execute the following command:

:helptags ~/.vim/doc

In case your interested, here are the other Vim-related packages that I have installed on my machine:

  • vim-common
  • vim-gnome
  • vim-gui-commom
  • vim-runtime
  • vim-tiny

Conclusion

And that’s it!  I now appear to have everything that I need to complete the beginning examples in Agile Web Development with Rails using Ubuntu 9.10 and Vim.

Update (1/20/10) – I added the sqlite3 package to the apt-get line above.  This package is necessary if you want to query your database manually.

Written by tpurl

January 5, 2010 at 6:42 pm

Cheapo Review Of The Nokia 2760

leave a comment »

My Nokia 6101 just died after 2.5 years of faithful, inexpensive service, so I was in the market for a new phone in a hurry. When I originally bought this phone, I hoped that Google would have revolutionized the cell phone industry in America, making smart phone service more flexible and inexpensive. Well, the changes that I want still haven’t materialized yet, so I went looking for a new phone that was as similar as possible to my old trusty Nokia.

Another requirement that I had was that I wanted the phone to work with the T-Mobile pre-paid service. I’m actually a really big fan of T-Mobile’s price and network coverage

The closest thing I could find was the Nokia 2760. On occasion, it would be available on th T-Mobile web site, but it couldn’t be found when my phone died. I therefore checked the Walgreens and Radio Shack stores in my town until I found one at “The Shack” (as the employees seem to be forced to call it). It was $40 plus tax, which means that I won’t lose any sleep if my daughter tries to flush it down the toilet.

To “activate” the phone, I simply took the SIM card out of my old phone and placed it in the new one. 20 seconds later, I was able to receive calls using my mobile number. I didn’t have to contact T-Mobile even once, and my old “plan” seems to work with the new phone very well.

The biggest questions that I had when I bought this phone were “what was missing from my old phone” and “what did I need to buy”. Here’s the results:

Missing

  • This phone doesn’t have any buttons on the outside like my old one did. I really liked having a volume and F-you button on the outside of the phone. The 2760 forces you to open the button to silence an incoming call, and I have yet to figure out how to adjust call volume without 5 button clicks.
  • I can’t record video on this phone like I could with the old phone. This isn’t really a bad thing, however, since the old phone’s videos were just god-awful.
  • Apparently, Nokia phones no longer come with a ringtone that sounds like a phone ringing. And I guess noticing that makes me some type of old fogie who can’t figure out why stores no longer carry Lawrence Welk LP’s. I tried to buy one from T-Mobile’s ringtone shop, but I couldn’t find one.
  • The 2760 doesn’t have a little antenna nub sticking out of the top.

Different & New

  • Bluetooth! I know I am the last person in America to buy a bluetooth-enabled phone, but I’m really enjoying it so far. On my 6101, I actually purchased the compatible serial cable from Nokia, which was around $50 if I remember correctly. I hate that I have to basically throw away that investment, but I am loving how easy it is to use bluetooth. Also, I purchased this bluetooth adapter from Newegg for $15, and it works very well on both XP and Ubuntu 9.04.
  • The software interface has changed a little bit, but it’s nothing too revolutionary. If you’re used to your old phone’s interface, then this one should be very intuitive.
  • I can now add MP3 ringtones from my MP3 collection. Sweet! Now I just need to find an MP3 of a phone ringing :)
  • I can log into Gmail with this phone, which I couldn’t do on my old phone for some reason. That’s nice, but the interface and network speed are nothing to write home about.
  • The battery model changed. My old phone’s battery model was BL-4C, and my new phone’s battery model is BL-4B. I don’t yet know if the two models are interchangeable, but I doubt they are.

What Hasn’t Changed

  • The wall AC adapter looks like it’s identical. Based on that, it doesn’t look like I need to buy another car charger.
  • The photo quality appears to be identical.
  • The phone still has a ridiculously small amount of storage. I think the official amount is 11 MB. Oh well, I already have a digital camera and an MP3 player, so I guess I don’t need a phone that does all of that too.

Conclusion

If you like little Nokia flip phones, then this one seems to be as good as its predecessors. I’m pretty happy with it so far, and it’s hard to beat the price.

Written by tpurl

December 8, 2009 at 7:02 pm

Posted in Review

Tagged with ,

Ubuntu 9.04 => 9.10 Upgrade

leave a comment »

I just finished upgrading my MythTv/printing/data/everything server from version 9.04 of Ubuntu to 9.10. For the first time, I tried using the Software Update program to upgrade my entire system, and it went surprisingly well. Here are some of the highlights; hopefully they will help a few other people.

MythTv

The OS upgrade included an upgrade of MythTv from 0.21 to 0.22, so I was a little nervous about how well mythbackend and all of my MythTv-related applications (like mythweb and nuvexport) would work. To my surprise, mythbackend and mythweb both upgraded flawlessly. This is a really impressive feat, and it reflects the hard work that the MythTv package maintainers put into each Ubuntu release.

The nuvexport package is broken for me, but I think that’s because I compiled a customized version of ffmpeg. Oh well, this seems to be a common hurdle when I upgrade Ubuntu.

One little thing that I did have to fix after the upgrade was my MySQL configuration. The upgrade laid down the default version of the /etc/mysql/my.cnf file (after asking, of course). This file was configured to block any computer from using MySQL over the network. This is bad for me, because I like to watch my MythTv movies from other computers using mythfrontend.

To fix this, I simply commented out the following line in my.cnf on my MythTv server by placing a # in front of it:

 bind-address            = 127.0.0.1

After that, I simply restarted MySQL and I was able to use mythfrontend from my other computers.

Note

If you are on a network with other untrusted hosts, then you will want to use a more secure configuration than this.

VirtualBox

I run Windows XP in a VirtualBox VM for work, so it’s very important that both VirtualBox and my XP image work properly at all times. Again, to my surprise, everything worked perfectly after the upgrade. I didn’t even need to re-install VirtualBox. The VirtualBox kernel module was automatically re-compiled during the upgrade process, so I didn’t even have to do that.

Please note that I was using the absolute latest stable version of VirtualBox (3.0.12) before I started the upgrade. Your mileage may vary if you are using an older version.

Overall

Again, I am very impressed by how well everything went. I don’t see why I would ever choose to do a fresh installation of Ubuntu again on this machine.

Caveat Emptor

The automatic upgrade process is far from perfect, and your results may be different. Before you start any major upgrade, make sure that you perform the following steps:

  1. Make a backup of all of your important files – I use rsnapshot to back up my important files daily, and it has saved my bacon more than a couple of times. Also, it’s a good idea to store this backup on a separate disk from the boot disk.
  2. Download the current and target versions of Ubuntu and burn them to CD’s – If things do go south, then you will want to be able to either reinstall the current working version of Ubuntu or the target version. Having the actual ISO’s available on a CD may save you a ton of time and grief.

Good luck!

Written by tpurl

December 1, 2009 at 3:36 am

Posted in Uncategorized

Tagged with , , , ,

Live TV On My EEE PC

leave a comment »

I apologize in advance for the corny, rhyming title :)

I’ve been using an Asus EEE PC 900 netbook for about a year now, and have used it mostly for light word processing and web browsing. I also have a MythTV server running in my basement on an old Duron-based system. I can do almost all of my personal daily work on the EEE PC, but when I need to do anything MythTV-related, I’m forced to switch machines.

This can be a pain, so I decided to try running the “frontend” for MythTV on my EEE PC. To my surprise, everything is working very well. It only took me about 5 minutes to install and configure the frontend software, and after that, I was able to do the following on my netbook:

  • Watch live tv
  • Watch recorded shows
  • Edit shows (i.e. cut out commercials)

And the best part is that it’s all working very well over my wireless G network. Your results may vary, but at least it’s nice to know that this configuration works for some people.

Here’s some more information about my setup in case you want to try this yourself:

  • My netbook has a 900 Mhz processor, 1 GB of RAM, and a solid-state hard drive
  • I am using the integrated graphics card made by Intel. Apparently, it uses the i810 chipset.
  • I am serving up standard-definition television

And finally, a few caveats:

  • I don’t know the limits of the video card that comes with my netbook. The highest resolution that I’ve tried is 1280×1024 on a 17″ monitor, and it looked pretty good. I have no idea how it would look at a higher resolution on a more regular-sized TV.
  • I have heard that his netbook simply can’t display HD recordings. I’m not an expert on this type of thing (since I don’t have an HD TV or monitor), however.
  • As with any hardware purchase, don’t buy anything based solely on a blog post or product review. This system worked well for me, but it could work terribly for you for a variety of reasons. Do a decent amount of research before you spend any money. For example, the MythTV wiki and mailing list are great places to do exactly this type of research.

Written by tpurl

November 24, 2009 at 6:50 pm

Posted in Review

Tagged with , , ,

Using My Creative Zen With Ubuntu 9.04

leave a comment »

I’ve been using an 8 GB Creative Zen player now for about a year, and in general, I’m very happy. It was about 25% cheaper than a comparable iPod, it can do more stuff, and it has ended up being very durable and easy-to-use.

Another thing that I initially liked about the Zen was how well it worked with Ubuntu Linux 8.04. From Amarok, I could add and manage files as easily as I could with my old iPod.

Then I updated my OS to use Ubuntu 9.04. The Zen would mount automatically when you plugged it in, but I couldn’t access it using any music player such as Amarok, RhythmBox, or Banshee. And if I could access the player using one of those apps, the connection was always very flaky. I might be able to move one or two songs, but eventually, something would crash and I would have to start over again.

This thread on the Ubuntu forums shows that many other Zen users were having the same problem:

The basic advice was to unmount the Zen after it was automatically mounted, and then access it using your favorite music player. This only worked for me sporadically at first. And if that wasn’t weird enough, the Amarok maintainers decided to do the following:

  • Completely change the Amarok GUI interface
  • Completely change the way you copy music to an MP3 player.

I figured almost everything out eventually, so I thought I would share it here.

  1. First, plug your Zen into your computer. You should now see a Zen icon on your desktop.
    • Desktop icon of a Creative Zen MP3 player
  2. Next, right-click on that icon and choose the Unmount Volume option. This may seem counter-intuitive, but it’s what you need to do.
  3. Next, open Amarok. If you don’t see the Amarok window after a minute, then look for the howling wolf icon in your task tray. You will need to right-click on it and choose Restore.
    • Note: This process may work with other music players, but I haven’t tested it.
  4. After Amarok opens, you should see the following items in Amarok:
    1. An MP3 player icon with a red X and green + next to it.
      • Zen icon from within Amarok
    2. Your Zen listed on the left-hand side of the screen.
      • File explorer listing for the Creative Zen from within Amarok
    3. If you don’t see it at first, then make sure that you have clicked on the Collection button on the left-hand side of the screen.
    4. Also, If you see the MP3 player icon but your player isn’t listed on the left-hand side of the screen, then click on the green + button.

Now you can copy individual songs from your Local Collection by right-clicking on a song or album and choosing Copy To Collection -> Creative Zen. That should do it. I’ve had pretty good luck with this system as long as I didn’t try to move over 6 albums’ worth of MP3’s at once.

And here are some of the differences that you need to get used to when using the 2.x version of Amarok:

  • You can no longer copy playlists over to your Zen. This is a big disappointment to me, and I can’t figure out why the Amarok maintainers took this functionality away.
  • You can no longer “queue” up MP3’s that you want to copy to your Zen and then copy them all over at once. Again, another great feature that was taken away for some mysterious reason.
  • Album covers are no longer copied to your Zen. This isn’t a huge disappointment, but it was always a nice feature of the pre-2.x version of Amarok.

In the end, I’m very appreciative that Canonical, the Gnome group, and the Amarok maintainers provide such excellent software that makes my life so much more enjoyable. And I’m glad that I finally figured out a somewhat-reliable process for copying MP3’s from my hard drive to my Zen.

Written by tpurl

November 18, 2009 at 7:43 pm

Posted in Tutorial

Tagged with , , ,

Notes On Installing Ubuntu 9.04 And Easy Peasy 1.5

with 2 comments

It’s unlike me to upgrade my systems very often since it can take so much time, but I was moved recently to upgrade both my “server” (to Ubuntu 9.04) and my EEE PC 900 (to Easy Peasy 1.5). In general, I’m very impressed with how much better Linux-on-the-desktop gets every 6 months, and I look forward to at least another 8 years as a happy desktop Linux user.

One of the great things about Ubuntu is that it really is just painless to set up some pretty sophisticated servers. For example, I use my Ubuntu server to record television shows using MythTv, which can be very difficult to install. However, using the Ubuntu packages, I was able to get my system up-and-running in less than 10 minutes.

I do have one very small criticism of Ubuntu, and it’s that they keep making it harder and harder to install ffmpeg from source. The “stock” version of ffmpeg that comes with Ubuntu can’t do a lot of cool things like convert videos to the H264 format, so one of the first things that I usually do after installing Ubuntu is compile a more robust version of that application. Well, the process I used to compile it in 8.04 definitely did not work with 9.04 for some strange reason. Thank goodness that I found this tutorial, which made things very simple.

One really great thing about the 1.5 version of Easy Peasy is that I can now use some Compiz effects with my EEE PC 900. Previous versions of Easy Peasy didn’t even allow me to turn Compiz on. Hooray for tons tap-dancing sprites on my screen!

Here are some of the resources that I used to set up my Ubuntu 9.04 and Easy Peasy 1.5 systems. Maybe someone else will find them to be useful:

Written by tpurl

November 17, 2009 at 6:47 pm

Posted in Review

Tagged with , , , , ,

Testing The Waters Of Jruby & JDBC

leave a comment »

I was recently tasked with writing a command-line script in Jruby that performed simple CRUD operations against a simple database table. I’ve written tons of scripts in the past that manipulated tables, but I had never done so using Jruby. I therefore decided to first write a “bare-minimum” test script that would help me dip my toes in this unfamiliar water.

I wanted to write my test script against a database manager that ran on my laptop, but I didn’t want to go through the hassle of installing and configuring Oracle or MySql. Also, I soon learned that a lot of Ruby database drivers don’t work with Jruby, so I needed a small, simple database that had a good JDBC driver. I ended up installing and configuring Apache Derby, and it worked out very well for me.

So anyways, here’s the script (jdbctest.rb):

 require 'java'
 require './derbyclient.jar'
 require './derbytools.jar'

 # This example assumes that you have the free DerbyDB software installed on
 # your machine.  It also assumes that you are running it in "server" mode by
 # executing the startNetworkServer.bat script.

 # This is what I'm using instead of Class.forName("org.apache.derby.jdbc.ClientDriver").newInstance()
 import 'org.apache.derby.jdbc.ClientDriver'

 connString = "jdbc:derby://localhost:1527/MyDbTest"
 conn = Java::JavaSql::DriverManager.getConnection(connString)

 stmt = conn.createStatement

 rs = stmt.executeQuery("select * from derbyDb")

 while (rs.next) do
     puts "#{rs.getString("NUM")} -- #{rs.getString("ADDR")}"
 end

 rs.close
 stmt.close
 conn.close()

I then placed the jdbctest.rb script in a folder with the derbyclient.jar and derbytools.jar file, and then executed the script like this:

 c:\Dev\jruby\somefolder>jruby .\jdbctest.rb
 180 -- Grand Ave.
 1910 -- Union St.

To make this script work, you need to do the following:

  1. Install Derby using this tutorial: Step 1 – Install Software
    • This is a very simple task that took me all of 6 minutes after downloading the software.
  2. Create the MyDbTest database and the derbyDB table using this tutorial: Step 2 – ij Basics
    • You should also populate this table using the SQL located under the Execute SQL Statements section.
  3. Once you’ve created and queried your table using ij, start your Derby server using this tutorial: Step 4 – Derby Network Server
    • You should validate the server using ij. Please see the Test network server connection with ij section in the Step 4 tutorial for help.

Please note that this might seem like a lot of work, but it’s really very simple, especially when you compare it installing and configuring most relational database managers. It took me about 20 minutes from A to Z, and I had no prior experience with Derby.

That’s it! I hope that this tutorial helps a few other people who want to get started with Jruby and JDBC.

Written by tpurl

August 21, 2009 at 1:09 pm

Posted in Tutorial

Tagged with , , ,

Why Treating Your Customers and Employees Well Is Great For Business

leave a comment »

I couldn’t agree more:

“For a business owner, there’s nothing more satisfying than watching honest dealers expand their operations while the schmucks, with their going-out-of-business markups, go down the drain.”

Written by tpurl

May 7, 2009 at 2:21 pm

Posted in Trackback

Tagged with , , ,

Administrative Scripting With Rake

leave a comment »

At my job as a middleware sysadmin, I’m a big fan of automating complex and repetitive tasks. It cut down on defects, saves time, and makes my job a heckuva lot easier.

In the past, I’ve automated many tasks using Apache Ant, and I’ve had pretty good experiences. It’s light-weight, easy-to-learn, and it integrates very well with Java-based software (which I very often use). The problem is that it’s not terribly flexible. If you want to use it to compile and distribute Java programs, then it’s a great tool. However, take it a few degrees out of its comfort zone, and things get significantly more complicated.

The problem seems to be that Ant-based build files are written in XML. XML’s a great language for declaring things in a device-independent manner, but it’s not a terribly good medium for writing programs. There are Ant extensions that make it easier to write build files that need to perform complex operations, but they haven’t really helped me much in the past.

Like I said, I’ve had a lot of success with Ant in the past, but every so often, I like to reevaluate the tools that I use. That opportunity appeared the other day when I was tasked with automating the deployment process for a new web application. I have been teaching myself Ruby for a little while, and have heard great things about Rake, so I decided to give it a try.

My First Rakefile

The automation script that I needed to write needed to be able to do the following:

  1. Copy some configuration files from one place to another. For example, if I’m deploying my application in the UAT environment, I would need to copy “config/db.conf.uat” to “config/db.conf”.
  2. I need to be able to specify my target environment (e.g dev, uat, prod, etc.) at runtime.
  3. Delete any temporary or backup files
  4. Create a WAR file
  5. Use that WAR file to create an EAR file.

The sixth and most important requirement was that this deployment script needed to be usable by people who had never used Rake or Ruby before. I therefore needed to give it a command-line help interface that was very simple and intuitive. I did not want to force other admins to learn Ruby just so they could use my Rakefile. Of course, I would like them to learn the basics of the language eventually, but nobody likes to be forced to learn new technology before they can see the benefits.

So here it is:

 1  require 'rake/clean'
 2
 3  CLEAN.exclude("**/*.bak")
 4  CLOBBER.include('build', 'dist')
 5
 6  task :default => [:usage]
 7
 8  ### Begin directory and file declarations
 9  directory "build"
 10 directory "dist"
 11
 12 file 'dist/myapp.ear' => 'build/myapp.war' do |task|
 13     puts "Building ear file..."
 14     sh "jar cf #{task.name} -C build myapp.war META-INF"
 15 end
 16 ### End directory and file declarations
 17
 18 desc "Usage statement for people who are unfamiliar with Rake or this particular Rakefile"
 19 task :usage do
 20     puts """
 21 Please execute the following command to build a deployable ear file:
 22
 23    jruby -S rake ear env=[dev|test|uat|prod]
 24
 25 For more task options, please execute the following command:
 26
 27    jruby -S rake -T"""
 28 end
 29
 30 desc "Make sure that an env var was passed to this build script"
 31 task :validate do
 32    if ENV['env'].nil?
 33        $stderr.puts "\nERROR: Empty env value"
 34        Rake::Task['usage'].invoke
 35        exit 1
 36    end
 37 end
 38
 39 desc "Update the environment-specific configuration files"
 40 task :setenv => [:validate] do
 41
 42    env = ENV['env']
 43
 44    webinf_dir = "src/myapp/WEB-INF"
 45    config_files = ['db.properties', 'soap.properties']
 46
 47    config_files.each do |config_file|
 48        cp "#{webinf_dir}/#{config_file}.#{env}", "#{webinf_dir}/#{config_file}"
 49    end
 50
 51 end
 52
 53 desc "Create a war file that can eventually be packaged as an ear file"
 54 task :war => [:setenv, :build, :dist, "clean"] do
 55    puts "Building war file..."
 56    sh "jar cf build/myapp.war -C src/myapp ."
 57 end
 58
 59 desc "Create a deployable ear file."
 60 task :ear => [:war, 'dist/myapp.ear'] do
 61     puts "The ear file has been created in dist directory"
 62 end

Ok, there’s a lot going on here, and it’s especially confusing if you’re new to Ruby. Here’s basically how I see things from a very high level:

Tasks And Prerequisites

Tasks are a lot like Ant targets, which are a lot like functions (although there are some big differences). They perform some unit of work, and are typically entry points into your script. For example, I could type in rake war, and I would immediately start running the instructions within the task starting at line 54, after the pre-requisites have run.

What’s a prerequisite? For the :war task, the pre-requisites are everything following the => notation. So when I attempt to run this task, the first thing that is actually executed is the :setenv task, followed by the :build task, and so on.

Directory and File Tasks

You may also notice that the :build task (at line 9) isn’t actually a task at all, but a “directory”. What I’m doing is specifying the directory at the beginning of the file, and then creating it later as a prerequisite for creating my war file. This seems a little strange to me, but apparently it’s a common way of doing things in Rakefiles.

Also, please note that if you do things this way, you save yourself a bit of coding. When you specify directories this way, rake takes care of recreating the directory after it’s been deleted and leaving it alone if it already exists. You can do this yourself with Ruby code, but why waste your time and energy?

Rake also has the concept of a file task. You can see an example of this on line 12, and it has the following basic syntax:

  • On the left side of the => operator, you have the name of the file that you want to create.
  • On the right side, you have the name of the file or files that will be used to create this file. Since my ear file is basically a war file with a little bit of added metadata, I only specified the war file for this task.
  • This is a little weird, but the task allows you to refer to itself. That’s what I’m doing with the task variable. And in this case, #{task.name} would be equal to dist/myapp.ear.

You might have noticed that I don’t really gain much by putting the code at line 14 into its own file task. I could have simply placed it within the :ear task, and saved a few lines of code and a little confusion. I’m doing it because this method of defining files seems to be more “idiomatically Rake-ish” to me, and that may make this file a little easier to change in the future.

Cleaning Up

What may be really confusing is that the clean prerequisite task isn’t defined anywhere. Well, it kinda-sorta is actually. At line 1, I require the rake/clean module. This tells rake that I want to use it’s built-in clean and clobber tasks. Traditionally, you use the clean task when you want to delete temporary files from your project, and clobber when you want to delete those files plus any files that can be recreated.

Next, I specify what I would and wouldn’t like rake to delete for me when I execute these tasks. At line 3, I’m telling rake that I don’t want to delete .bak files when I clean house. At line 4, I’m saying that when I really want to clean things up in my project (without affecting anything that I can’t replace), I also want to delete the dist and build directories, which contain my ear and war files respectively.

Shell Interaction

Once my :war task is finally done with its prerequisites, it can finally execute the code within its block. Line 55 simply prints a string to STDOUT, and line 56 simply executes the jar command to create a war file. Please note that rake has built-in versions of common shell commands such as mkdir, cp and sh that work across platforms. This is a very nice feature to have, and saves me a bit of coding time.

Command-Line Arguments And Help

Since I wanted to be able to specify build properties from the command line, I added some common command-line tools to my script. This is first implemented at line 42, within the :setenv task. There, I’m reading the value of the env parameter that was passed to the script at runtime.

Of course, before I assume that a parameter exists, I need to validate it. Tht’s why the :settenv task has the :validate task as a prerequsite. It checks to see if some env value exists. If it does, the task exits normally, but if it doesn’t, two things happen:

  1. I print an error message to STDERR
  2. The :usage task is invoked
  3. The script exits with a non-zero return code

The second step should be pretty easy-to-understand by now. I simply invoke the :usage task, which does nothing but print usage information. Also, please note that the :usage task is defined as my default task at line 6. This means that if someone just types rake in my project’s root directory, they will see a usage message.

The third step surprised me. A lot of build tools (including Ant) don’t really make it easy to just exit a build script, especially if you want to return an error code. Since Rakefiles are just Ruby scripts, I can use a very common scripting idiom to exit my script in a somewhat-graceful way.

Questions

Here are some of the questions that went through my mind while I was writing this:

Is Rake better than Ant?

This is a big judgement call, but Rake definitely has its advantages. I like the fact that my build file is an actual script, not an specification of a process written in XML. If I was building a big Java program, I would probably stick with Ant since it has better Java integration. However, for my relatively simple projects, Rake could be a very useful tool.

Why not just write a regular Ruby script instead?

  • Command-Line Interface Consistency
    • Anyone running a Rakefile always executes the same command: rake [task] [paramN=foo]. This interface consistency makes it easier to properly run a Rakefile without knowing a lot about what it does.
  • Code Reduction
    • Rake is program and a framework (DSL?). This framework gives you some nice built-in stuff that cuts down on your total lines-of-code while improving script quality
  • Dependency Based Programming
    • Martin Fowler explains (in his rake tutorial) why it is so much easier to use Rake to write these types of scripts.

Written by tpurl

March 31, 2009 at 5:15 pm

Posted in Tutorial