Setting up Ubuntu for Ruby on Rails development

NOTE: This is a work-in-progress. I’m publishing it early so that Sam can use it. If it doesn’t work for you exactly as expected, well, that’s to be expected.

Every time I setup a new Ubuntu machine, I have to search around to come up with a procedure for getting everything I need to develop Ruby on Rails apps. Here it is pre-packaged.

(The configuration below is based on my current preferences: Ubuntu 9.04, ruby 1.8, rails 2.3.2, mysql 5, subversion plugin for Eclipse (subclipse), Eclipse with Aptana and RadRails. Ruby 1.9 is starting to gain momentum, but I haven’t used it yet. Oh, and most of the instructions below are for command line users. Try it. You’ll like it.)

After installing Ubuntu 9.04 (which is not covered here), install Eclipse, subversion, ruby and mysql like so:

sudo apt-get install eclipse ruby libmysql-ruby mysql-client mysql-server irb
mongrel rdoc ri ruby-dev rubygems subversion

The first thing to note is that while Eclipse works with the out-of-the box java installed with Ubuntu 9.04, Aptana does not. So install the Sun Java JRE like so:

sudo apt-get install sun-java6-jre

Then, configure the system to use the new java by default:

sudo update-alternatives --config java

With Eclipse, you can’t rely on the command above to make it use the Sun Java. So, edit the Eclipse configuration file:

sudo nano /etc/eclipse/java_home

Comment out the java-gcj line and add a line for sun just after it:

#/usr/lib/jvm/java-gcj
/usr/lib/jvm/java-6-sun

Fire up Eclipse from the Applications menu. (Applications -> Programming -> Eclipse). Then, install the Aptana plugin. Within Eclipse, click on Help -> Software Updates -> Find and Install -> Search for New Features to Install. Add a new Remote Site for updates with the following URL:

http://update.aptana.com/update/studio/3.2/

Make sure it is checked, then click Finish. Eclipse should then walk through the Aptana installation. After restarting, you’ll see the Aptana welcome screen. Look for the link which will install RadRails. Once you’ve done that, it is time to install subclipse–the subversion plugin for Eclipse. Go to Help -> Software Updates -> Find and Install -> Search for New Features and create a new remote site with the following URL:

http://subclipse.tigris.org/update

Go through the same steps from the previous step to add the SVN client.

That’s it for the installation. You’ll probably want to customize some settings in Eclipse. Make sure the settings for the ruby interpreter, rake, mongrel, etc.  are accurate. I like to turn line numbers on in the Text Editor preferences.

Your project may require one or more “gems” for ruby. Most can be installed with a command like this:

sudo gem install [gem-name]

Of course, you haven’t even installed rails yet. So do that:

sudo gem install rails

One gem you’ll need is rake. The rake package from the Ubuntu repository is old. Get the new one and then symlink it to make it more accessible:

sudo gem install rake
sudo ln -s /var/lib/gems/1.8/gems/rake-0.8.4/bin/rake /usr/bin/rake

And, it isn’t a bad idea to put the gems’ bin folder in the system path so things like autospec work correctly. To do so, create this file:

sudo nano /etc/profile.d/gems.sh
# Here's the one-line for the file:
export PATH=$PATH:/var/lib/gems/1.8/bin

Reboot or just logout to trigger it. This wordpress editor is super annoying, so I’m done now.

Advertisements

Rain8net Ruby Library v1.0.0

I previously wrote about a product called Rain8net. I’m happy to announce the initial release of my Rain8net ruby library. The library is now available from rubyforge.org.

Or, just install it like this:

gem install rain8net

Now you won’t have to worry about sending the specific codes I detailed in my last post. Controlling your sprinklers is as easy as:

r8 = Rain8net.new
r8.turn_on_zone(1)
r8.turn_off_zone(1)

See the online documentation at the project homepage for more information.

Build a Development Infrastructure…or buy a Mac

Disclaimer: Let me start out by saying I am not anti-Mac. That being said, I am very pro-Linux. I am not a Dell lover either. I just picked them for comparison.

As a web developer, I have found it extremely beneficial to have access to my own servers for development purposes. I have my own infrastructure for version control. I maintain my own DNS servers and can quickly provide access to a temporary site for clients.  While developing TheBigFork, I developed several long-running data cleanup scripts. These would not have been possible without an always-on server to do the work.

Great. So, what does that have to do with buying a mac? Nothing, really. I recently have become aware that more and more web developers (especially Ruby developers) are developing on a Mac. Frankly, I don’t get it. I’ve tried it, and it doesn’t come close to developing on Linux. But, that’s really a discussion for another day. This article is about price.

I compared the price of a MacBook Pro 17″ 2.5 gHz notebook with a collection of Dell machines. The MacBook is listed at $2799. For that much money, you could buy:

Seven Dell Vostro 200 desktops with a 20″ widescreen display and a 250 gig hard drive. These come with Windows XP, but you can easily reformat it and install Ubuntu or Fedora. Doing so opens up a whole world of freely available open-source software. (And, don’t argue that Linux isn’t ready for the desktop. If you can switch from Windows to Mac, you can easily make the switch to Linux.)

With 7 computers, you can hire a receptionist, bookkeeper and project manager and still have a few extra machines for some junior developers. Granted, these aren’t the most powerful machines out there and they probably aren’t worthy of acting as a server–unless you’re desperate.

Here’s another scenario. Buy a Dell PowerEdge 840 server plus a Dell Precision T4300 workstation (which alone rivals the macbook’s specs). The only problem is, you’ll have almost $1400 extra. I guess you’ll have to buy a Dell Latitude D830 laptop for working on-the-go, and a second 21″ monitor for your workstation. Wait–you still have extra money. So, grab a Vostro 200 from the previous scenario. Now you have four machines: a server, a high-powered 64-bit workstation, a nice notebook and an extra desktop for your assistant.

If you really need a laptop with more horsepower than the MacBook, just get the Precision M6300 mobile workstation instead of the workstation and notebook above. You’ll still have enough for a server and the spare desktop.

Finally, if computers aren’t your thing, put a down-payment on a nice new car!

Bottom line: Macs are very nice. To me, they are simply not worth the extra cash–especially when you have work to get done.

In case you’re wondering, the best Ruby IDE that I’ve found is Aptana Radrails which runs poorly on Mac and excellent on Linux. Textmate is the Ruby IDE of choice on Mac. I found it lacking in features and difficult to use.

Hostmonster on Rails

A client of mine recently moved their web hosting to Hostmonster, and I was tasked with migrating a Ruby on Rails application to the new server. I ran into a few snags.

First of all, I followed their tutorial.

The default rails welcome page worked fine, but I kept getting “Application Error” on everything else. The logs showed nothing. I found several message board posts pointing to the permissions on the “public” folder.  Dr. Chuck had the best article on the subject.

Dr. Chuck’s instructions fixed the problem for a month or two.  Then it stopped working again. I figured some server-side process had changed the permissions on my files. So, I set it up again. It still didn’t work.

I actually had to contact tech support. A couple of days later they responded with the solution (thankfully, this isn’t a mission-critical app). Hostmonster had recently updated to a newer version of Rails. So, I just commented out the version in the rails environment file:

#config/environment.rb
#...
#RAILS_GEM_VERSION = '1.2.5' unless defined? RAILS_GEM_VERSION

I believe that tells the application to use whatever version of rails it can find (the most recent version on the server). Since version 1.2.5 had apparently been replaced with 1.2.6, removing the declaration for 1.2.5 fixed the problem.

The part that still confuses me is, I had tried generating the application from scratch while logged into the Hostmonster server (via ssh). Doing so still generated an environment.rb file for version 1.2.5.

Of course, the other part that confuses me is why did 1.2.5 stop working?  When I update my own servers with ‘gem update’, I keep old versions available for backwards compatibility of existing rails apps. As far as I know, there is no problem doing it this way. Am I wrong?

Converting DivX files to mpegs for an NTSC DVD

Problem:

You have a bunch of DivX avi files and want to put them on a DVD for a friend. The friend wants to play the final product on a DVD player (not on a PC).

Solution:

Believe it or not, my first inclination was to fire up my old Windows XP computer because it has all of the Sony programs on it–including DVD Architect. To make a long story short, Windows proved itself once again as an inferior system. The DivX files have to be converted to mpeg. I tried several converters which ran for hours at a time. I finally had 3 converted files ready to burn. I thought everything worked fine until I played the DVD on a machine. It looked horrible and skipped a lot…unacceptable.

Fortunately I have Linux which helped produce a much better final product. My originals were all 16:9 widescreen, but I wanted to make them work on a 4:3 system. After installing ffmpeg (on Fedora, do this: sudo yum install ffmpeg -y), here is the command I used to do the conversion:

ffmpeg -i originalfile.avi -target ntsc-dvd -aspect 4:3 -s 720x400 -padtop 40 -padbottom 40 outputfile.mpg

Looks hairy, but it works well. I discovered the actual size of my original files are 720×400 by looking at the output of ffmpeg. So I kept this size and padded 40 to the top and bottom to create the letterbox. For reference, here some sample output from ffmpeg:


Seems stream 0 codec frame rate differs from container frame rate: 30000.00 (30000/1) -> 23.98 (24000/1001)
Input #0, avi, from 'filename.avi':
Duration: 00:44:12.1, start: 0.000000, bitrate: 1239 kb/s
Stream #0.0: Video: mpeg4, yuv420p, 720x400, 23.98 fps(r)
Stream #0.1: Audio: mp3, 44100 Hz, stereo, 112 kb/s
Output #0, dvd, to 'filename.mpg':
Stream #0.0: Video: mpeg2video, yuv420p, 720x480, q=2-31, 6000 kb/s, 29.97 fps(c)
Stream #0.1: Audio: ac3, 48000 Hz, stereo, 448 kb/s
Stream mapping:
Stream #0.0 -> #0.0
Stream #0.1 -> #0.1
Press [q] to stop encoding

Then I decided to wrap it in a little perl script so I could do all 24 of the files without sitting around watching the progress:


$dir = '/home/adam/';
chdir($dir);
opendir(DIR, $dir);
@files = readdir(DIR);
closedir DIR;


foreach (@files) {
next unless $_ =~ m/^([\w\.]*)\.avi$/i;
# This should all be on one line...
print `ffmpeg -i $_ -target ntsc-dvd -aspect 4:3 -s 720x400 -padtop 40 -padbottom 40 -y $1.mpg`;
}

As usual, this is mostly for my reference, but maybe somebody else will also find it useful.

MythTV on Ubuntu plus IRman

I’ve been running mythtv for a couple of years. It is much more flexible and feature-packed than any commercially available DVR. Last week Sam told me that the free service for the TV listings has closed up. There is a new fee-based service from Schedules Direct. Unfortunately, I was still running mine on Fedora Core 3, and a fairly old version of mythtv itself. The SD service requires the latest version.

So, I decided it is time to update & upgrade. I went with Ubuntu on both the backend and frontend. Why? Well, I’ve noticed Fedora is difficult to upgrade to the next version and package maintainers for mythtv tend to drop old distros. Ubuntu is fairly simple to upgrade–even without downloading a new install CD. So, hopefully it will be easier to keep up to date.

There are some nice metapackages for mythtv in the Ubuntu repositories (can’t remember which ones–but they show up in Synaptics Package Manager). The backend version installed everything I needed and even setup the initial configuration. Oh, and my Hauppage PVR-150 required zero configuration. It just worked! I did have to update the packages with the latest build from mythbuntu in order to use the SD service. But they have easy instructions for doing it.

The frontend was a little more tricky. Using the “ubuntu-mythtv-frontend” metapackage was pretty sleak. It adds a mythtv user and enables auto-login; and it starts the OpenBox window manager and the mythtv client automatically when the machine boots up. That made it tricky to disable the screensaver since I couldn’t find a config file. So here’s the secret:

1. Let it boot up like normal. Then exit the mythtv client.

2. You’ll see a countdown for the auto-login. Login as some other user (you probably created one when you installed Ubuntu.) From there, change the password for the mythtv user using the admin tools. Make sure you know what the password is. Then log out.

3. The countdown will show up again. Type the username ‘mythtv’. Don’t enter the password yet. From the options menu, set your session to Gnome. Then go ahead and login with the password you created in step2.

4. When it asks you if you want to change your default session to Gnome–or just use it for this one session, be sure to tell it you only want Gnome for this session.

5. Use the regular screensaver tool to disable it. Then log out.

All set.

Now, I also mentioned IRman in the title. I’ve had one for years, but I never could get it working. I decided to make it work this time. Just my luck, IRman support is broken in the current version of lirc. The site says there is a fix in the CVS version. Cool.

So, I downloaded the CVS version and tried to build it. There must be something broken in the configuration scripts, because it never started configuring anything after I exited the menu. So, I tried the latest CVS snapshot (v0.8.2pre3). That installed fine, but IRman still didn’t work.

(Oh, by the way, the irrecord tool worked fine to setup the remote, but lirc itself wouldn’t respond using the IRman.)

After trying all sorts of versions, here’s what finally worked:

1. Download the latest CVS snapshot mentioned above. Extract it.

2. Checkout the latest files from CVS. Copy the contrib, daemons, doc, drivers, remotes and tools folders from the CVS folder to the folder you extracted to in step 1.

3. Run “configure.sh” and choose “IRman” from the “Other Serial Device” menu. When you save and exit the program, it will configure lirc. Then just “make” and “make install” the lirc package.

I probably should mention, you’ll want to uninstall the Ubuntu version:

sudo apt-get remove lirc

When I did this, it kept my lirc startup script in /etc/init.d, but I had to modify it since lirc installed itself somewhere else. To find it, just do:

which lirc

(or maybe it was “which lircd”)

The rest of the setup for a mythtv remote is pretty simple. There are plenty of writeups once you get past this point. Here’s one:

http://www.keeto.net/articles/mythtv_lirc_irman.html

So, there you have it, my very unclear instructions.

Using RubyODBC in Rails on Linux to connect to MS SQL Server

(I really need to work on shortening my titles.)

I spent the day trying to figure out one little problem. I setup a brand new server for the Intranet at work. I set it up with Fedora 7 and started configuring it for my rails apps. Since our corporation has decided to use Microsoft SQL for all databases, I turned to the instructions on the Rails wiki to setup ODBC.

Most of it went pretty smoothly. When I was done, I launched mongrel and checked the site using http://ip_address:3000. It all worked great. So, then I setup mongrel_cluster and fired it up. No workey. I kept getting database errors saying “No data found.”

The very misleading error was hard to solve. I finally found a post which explains that there is a bug in RubyODBC which does not play well with “text” columns that are blank. So, the answer is to set all your blank fields to NULL. Well, I couldn’t figure out how to do that. (MSSQL is not my favorite.) I finally figured out to use a whole bunch of these queries in SQL query analyzer:

UPDATE tablename SET description=" " WHERE description LIKE ""

(There’s a space between the first set of quotes, but not the second.)

So, that fixed everything for now, but I also had to make sure it doesn’t happen again. I couldn’t get the default value in SQL to do what I needed, so I added a bunch of these in the model code for each problematic model:

def before_save
if self.description.blank?
self.description = ' ' #(two spaces)
end
end

Hopefully this will help somebody else.