Deploying CruiseControl.rb with Custom Tasks

More and more work is being done by geographically disparate teams these days, so a continuous integration tool like CruiseControl.rb is quite useful. Andre and I could have used this when we were heads down with GeoKit. But better late than never, right?

I decided I would make an attempt to deploy CruiseControl.rb to one of the hosts that I have — and do so with Capistrano. For the most part, it was pretty painless, but I did run into a gotcha or two.

First, the host I deployed to uses the Apache / Lighttpd (fastcgi) style of deployment. Unfortunately, Lighttpd just would never start up for me! After way too long, I finally figured out that I had DOS line breaks in my file that I could not see. So I zapped them with dos2unix and all was well. Unfortunately, this ate up a lot of my time as I’m not very skilled at debugging fastcgi issues.

CruiseControl.rb is a Rails app, but not your typical Rails app. It uses no Rails app, but rather stores your project information in a projects directory underneath the app root. Further, its more than just a Rails app, it utilizes additional processes as project builders.

To deploy with Capistrano, you have to preserve the projects directory so that it will persist across your releases. That’s pretty easy to do with symlinks, so that’s a piece of cake. You can use the after_update_code callback to do this.

There are two other use cases that I could see that I would need. Adding a project and starting a builder for that project. To enable those, I added Capistrano tasks for each. Both tasks rely on environment variables and both tasks could probably benefit from a bit more error-checking, but they are good enough for me.

So to start a project, I use:

NAME=GeoKit URL=svn://rubyforge.org/var/svn/geokit cap add_project

to start its builder, I use:

NAME=GeoKit cap start_builder

I added my custom tasks under config/recipes/cruisecontrol.rb and required this in deploy.rb. The custom tasks code is below:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
Capistrano.configuration(:must_exist).load do

  desc "Update symlink for projects directory."
  task :after_update_code do
    run <<-CMD
      rm -rf #{release_path}/projects &&
      ln -nfs #{shared_path}/projects #{release_path}/projects
    CMD
  end

  desc "Add a project to cruise control."
  task :add_project do
    unless ENV['NAME'] && ENV['URL'] 
      raise ArgumentError, "***** You must specify the NAME and URL parameters to add a project. *****" 
    end   
    run "#{current_release}/cruise add #{ENV['NAME']} --url #{ENV['URL']}"
  end
  
  desc "Start a builder for a project."
  task :start_builder do
    raise ArgumentError, "***** You must specify the NAME of the project to build. *****" unless ENV['NAME'] 
    run "#{current_release}/cruise build #{ENV['NAME']} &"   
  end
end

And with that, any of my projects can now be monitored with CruiseControl.rb.

A few caveats.

  • I had to physically edit the cruise_config.rb file (on the server) for the project to include my email address and polling interval. No big deal, its a one-time thing.
  • If your code is proprietary, you may want to protect the site with
    basic authentication to keep unwanted eyes from seeing your project assets.
  • Since your project data is on your server’s file system, you may want to consider a backup strategy if you value your build history.

Suggestions for ThoughtWorks:

  • Consider including Capistrano tasks to make it easier — mine are admittedly rough, I’m sure.
  • Consider adding some element of authorization by project. For example, I have public plugins, but I also have proprietary code that I do not wish to share. Obviously, its easy enough to deploy a second site, but that’s mildly inconvenient.

I hope this is helpful to continuous integration fans out there trying to get set up!

Posted in Open Source, Ruby, Ruby on Rails | 4 Comments

GeoKit: A Tiny Update

Its been a while since I tinkered with GeoKit, but when I read this post, I thought I’d take a look at a couple of things that were mentioned.

James wrote that it would be nice to be able to reset the default_units value to enable localization.  Well, actually you can.  :default_units is modifiable through a class accessor.  Also, you can pass an optional parameter in your finders called :units which enables you to override whatever default value you’ve set.

While we’re talking about defaults, I applied a patch submitted by Hoan Ton-That which enables you to specify your preferences for units and for the formula from within the environment files.  So these preferences would appear right along side your API keys for GeoKit.  Its a small feature, but you may appreciate it.  Thanks Hoan!

Otherwise, James mentioned that :include support is lacking with GeoKit.  That’s not entirely true.  I added a passing test case which successfully pulls columns from a belongs_to relationship.  I suspect that the has_many relationships are the problem.  But if your case is covered by the belongs_to relationship, then you are covered.

There is a less-used method called distance_sql which enables you to just get the distance calculation in SQL form.  You would use this if you ever found that GeoKit could not support your exact query requirements.  Its less elegant for sure, but saves you the trouble of having to code the distance calculation.

UK geocoding is still in the roadmap, but both Andre and I have a few other projects and side endeavors going on.

Posted in GeoKit, Open Source, Ruby, Ruby on Rails | 4 Comments

What's your Tech Stack?

I have been assigned a “little buddy” at work to become my replacement — do you think they know something?  This is the first move toward redundancy in quite some time, so maybe so.

Anyway, so I started asking some basic questions of this guy to assess where to start with the transitioning.  Unfortunately, my initial questions included Spring Framework, MVC, servlet, but all received negative responses.  And then when I got up to draw on the whiteboard I asked if he knew UML.  Negatory.

Its not his fault, of course, but I started thinking how hard it is to replace someone like me.  I’m sure this will come off arrogantly, but I don’t mean it to be.  The fact is, at my level, I know lots of stuff.  And you can’t just parachute a warm body into place and expect a replacement in two months.  I’m basically going to have to build this guy from the ground up.

So it led me to wonder what our tech stack is.  And so I started to draw it out for him just as a means to highlight what we needed to cover and why we needed to meet daily from now on.  In no particular order, here are some technologies and tools that I deal with.  And I’m sure I’ll leave some obvious ones out:

Java, JSP, JSTL, Freemarker, Spring Framework, Acegi Security for Spring, EhCache, Tiles, Sitemesh, Log4J, Ant, RegEx, JUnit, HTTP, SOAP, XML, XHTML, CSS, SQL, Bash Scripting, Solaris, Windows, DOS, Intellij, Toad, Subversion, Test Director, Inquira, Sun One Web Server, Apache, WebLogic, Alteon, Visio, Oracle, Firefox, Firebug, IE, Siteminder, CAS, SSH, Telnet, AppGate, SCP, UML, RSS, Checkstyle, JCoverage, etc.

I’ve left out the obvious ones like Word, Excel, and Outlook.

Looking at the list that I know is probably woefully incomplete, I can’t help but think that most management and most business folks grossly underestimate us.  So its no wonder, they deal me a newby.

For my Rails and Ruby audience, obviously there’s a slew more elements that I could have added, although the cool thing about Rails is that your tech stack compacts quite a bit as has been pointed out by many before me.

Posted in Business Strategy | Leave a comment

Why IT Sucks

Just to be clear, IT in this context means being in an IT department, not being in the IT industry.

I’ve spent a combined five years in IT departments of two companies — one a large company another a small company. In each case, the experience lacked job satisfaction and only marginally advanced my career. If you find yourself faced with a job opportunity in an IT department, consider the following to be likely experiences:

  • You will be frustrated because technology is not the core business. And unfortunately for you, this means that you aren’t likely to be the rockstar of your company. You are an enabler of minimal importance in a cost center.
  • You will deal with technology that is likely to be obsolete or on the verge of obsolescence. In IT, it is not important to those you serve what the technology is, rather its whether the solution provides the desired value.
  • You will integrate with old technologies or products that have challenging integration scenarios. As you are the tail on the dog, no one will ask you your opinion for the products that are most likely to integrate well with your technology stack. Rather, you will be brought in after such products have been selected.
  • You may find that the talent around you is watered down. The trend is to cut costs which inevitably leads to outsourcing. In my experience, outsourcing provides less talented, less instinctive colleagues. These will be your teammates.
  • You may find that cost cuts means there is little investment in the “factory” that you work in. Hardware and software that could make your life easier are not accessible due to budget challenges. Therefore, the factory eventually resembles an old car plant with declining efficiency.
  • Your managers may care only about your utilization and your costs. Innovation is secondary to these factors, so you may have trouble championing new ideas.
  • You may find in bigger companies that consensus-building consumes most of your time. Be ready for double-digit emails per day with people copying you on details that are irrelevant to your job.
  • You may find that the company has organically grown in layers causing you to fight through multiple layers just to get simple tasks done. As such, simple tasks are hard tasks and hard tasks are impossible. If you think that something as simple as opening a firewall port can’t take weeks, think again.
  • You may find that since the company has cut costs to the bone that you end up wearing more hats than you feel qualified to wear. You will be best prepared to succeed if you can write your own requirements, write code, write markup, develop your own styles, be your own DBA, be your own system administrator, and do your own testing. You will most likely have to build your own infrastructure enablements because those would be too costly to be purchased for you.
  • You may never understand the business decisions made by those who ultimately create your projects. You may question whether they know how to scorecard, perform cost-benefit analysis, or whether they even know their business. But in the end, you will have no choice but to work on their projects.
  • You may find that your natural curiosity for new technologies or business strategies is not appreciated or valued. Old school managers may even make fun of you for having your nose in a book reading about those “new-fangled” technologies. Be prepared to have uninspired leadership.
  • You may find that your colleagues eventually have become zombies. They show up every day and walk the halls, but they seem to be in an unproductive, unchanging funk. And worse, you may recognize yourself making the same transformation.

Is it really this bleak? Yeah, I think so. What should you do?

If you must work in an IT department, do so as a contractor so that you can limit your long-term exposure if you find the environment toxic. If you can only join as an employee, then be prepared to highlight job security and a regular paycheck as the best part of your job. Be prepared to be held hostage by those same qualities.

If you are a technician on the leading edge of standards and new technologies, you will only be happy working with like people. These types of people work where technology is the core business. They work for companies where technology is the product — or technology enables the product. So your next job should be at a company that matches this profile.

If you are in an IT department now, your job is to sharpen your skills — probably on your own time. Your challenge is to plot an exit strategy and execute on it methodically, but without losing your spirit. If you are successful, maybe one day we’ll be co-workers. If you get there first, keep a chair warm and I’ll see you soon!

Posted in Business Strategy | 66 Comments

Taming the Beast

In my continuing efforts to work Ruby and Rails into the Enterprise, I’ve been working on adapting Rick Olson and Josh Goebel’s Beast discussion forums engine. Its excellent work on their part and quite fun to play with.

My adaptations are:

  • Modify user authentication to use our LDAP user repository — so users can just use their existing credentials
  • Using YUI Reset, Fonts, and Grids throughout
  • Modifying the markup to be slightly more semantic
  • Adding Digg-style pagination
  • Applying design inspiration from Odeo, SimpleBits, and Cork’d as well as others.

I’m not done yet, but its starting to look pretty decent. Here’s a peek:

Posted in Open Source, Ruby, Ruby on Rails, YUI | 2 Comments

GeoKit: Going International?

We have been asked whether GeoKit could be made to support UK addresses and this is something that we’re interested in doing.  I must admit that I was incompletely uninformed as to how different these addresses really are.  Just have a look at Wikipedia has to say about UK addresses.  In specific, we’ve been asked to support this geocoding service: www.postcodeanywhere.co.uk.

So since we’re looking into this, I thought it might be a good idea to solicit other suggestions for geocoding services and address variants which GeoKit doesn’t already support, but which would be useful to the Rails community.  It appears there will be some refactoring involved, so it makes sense to do a little due diligence by broadening the input process.

So drop me or Andre a note or comment and let us know.

Posted in GeoKit, Ruby, Ruby on Rails, Uncategorized | 5 Comments

Who is doing Rails?

The recent GeoKit publicity has caused an influx of new visitors to this blog. Now that the traffic is subsiding somewhat, I thought I’d take a look at the geography of Rails. It seems an appropriate tangential GeoKit topic.

So have a look at the map. 44% of the traffic came from the United States — looks like the East Coast and West Coast primarily. Next, came Germany at close to 9% — Berlin mostly. Canada came in at 7%. 17% of the traffic came from smaller countries.

I find this pretty fascinating and definitely flattering that such a wide range of people would pay a visit to this blog.

Posted in GeoKit, Ruby, Ruby on Rails | 3 Comments

GeoKit: More Syntactic Sugar

We just checked in code which improves the readability of GeoKit’s finders. Its quite obvious from the code, so just take a look at these examples:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
# Find the nearest store.
stores = Store.find(:nearest,  :o rigin => an_origin)

# Find the farthest store away.
stores = Store.find(:farthest,  :o rigin => an_origin)

# Find within a radius.
stores = Store.find(:all, :within => 5,  :o rigin => an_origin)

# Find outside a radius.
stores = Store.find(:all, :beyond => 5,  :o rigin => an_origin)

# Find within a range.
stores = Store.find(:all, :range => 5..10,  :o rigin => an_origin)
Posted in GeoKit, Open Source, Ruby, Ruby on Rails, Uncategorized | 6 Comments

GeoKit: Improvements to distance_between and distance_to

Over at Earthcode, a request was made to enable the distance_between and distance_to methods to accept physical locations in pre-geocoded string form. I have added this improvement, so you can now do:

1
2
3
4
5
6
7
# Geocode from and to, then calculate the distance
# between them.
dist = Store.distance_between("Irving, TX", 
                              "San Francisco, CA")

# Geocode the to, then calculate the distance to it.
dist = irving.distance_to("San Francisco, CA")

Andre has also added further flexibility to the :o rigin to include setting it to an array of lat / lng values. Usage looks like:

1
2
3
# Presumably some previous geocoding and then this:
stores = Store.find(:all,  :o rigin => [37.792,-122.393], 
                    :conditions => 'distance < 10') 

Keep the feedback coming!

Posted in GeoKit, Open Source, Ruby, Ruby on Rails | 3 Comments

Restore CSS Inspection in Firebug on Windows

At work, I work in a Windows XP environment and noticed that Firebug would not allow me to inspect CSS.  Since I do mostly Java, I hadn’t worried about that.  However, today, I had to debug a stylesheet problem in one of our apps.  When I couldn’t easily figure it out through brute force techniques, I decided that I really needed to restore Firebug’s ability to inspect CSS.

The message it gives is that the DOM Inspector is not installed…except that it was in my case.  So that was pretty perplexing.  However, Firebug itself points you to an FAQ which in turn points you to a forum entry.  The grammar isn’t great, but the basic steps are:

  1. Find your Mozilla directory within your application data directory and make a backup of it.
  2. Go to the Control Panel and remove Firefox from your programs list.
  3. Go to the directory where Firefox used to be fully installed and remove it (the uninstall doesn’t do it for you).
  4. Download and install Firefox, but in a different directory than the original installation.
  5. Restore your application data if it has been removed.

Some of these steps make no sense, but I followed them blindly and it worked.  I’m pretty sure that the process can be streamlined, but since I’m up and running I’ll leave that to someone else.  Since this was hard to find and harder to understand once found, I thought I would write it up for anyone who might need to do the same thing.

Posted in CSS, Firebug, Firefox, Open Source | Leave a comment