Installing Rails on Mac OS X Tiger (10.4.8)

Just a few days ago, I had the opportunity to upgrade my iMac from a 20” to a 24”. Not only does it have more real estate on the screen, not only is the CPU slightly faster, but it also can take up to 3 Gb of RAM, from 2Gb, which is quite an improvement, especially if you like to run multiple VMs (using Parallel).

So it was quite a relief to us my notes to install Rails on Mac OS Tiger. Except that a lot has changed in the past 3 months since I last wrote that article, and before I update the page to make more sense to newcomers, I’ll just write down a few notes on what I had to do differently.

These reflect the installation on MacOS 10.4.8 and the latest version of MacPorts (as of 10/14/06).

First of all, Darwin Ports is no more: long live MacPorts!

Which means that here is a new location for darwin ports installer.

Then I uncovered a problem in the order of the steps:

Set the PATH before running “sudo port -d selfupdate”, not after as suggested.

One thing that I did not realize, is that you need to actually install a C compiler before you can get started! The easiest is to install XCode 2.4. There is a free registration you need to fill in.

I missed a sudo:

cp httpd.conf.sample httpd.conf => sudo cp httpd.conf.sample httpd.conf

The path to the launchctl file for apache2 has changed:

sudo launchctl load -w /Library/LaunchDaemons/org.macports.apache2.plist instead of sudo launchctl load -w /Library/LaunchDaemons/org.darwinports.apache2.plist

To initialize the database, you need to add:

add "sudo -u mysql mysql_install_db5"

The path to the launchctl file for mysql5 has changed as well:

sudo launchctl load -w /Library/LaunchDaemons/org.macports.mysql5.plist instead of sudo launchctl load -w /Library/LaunchDaemons/org.darwinports.mysql5.plist

replace rb-mysql5 with rb-mysql since rb-mysql supports both flavors

And that’s where it got a bit tricky. With that combination of MacOS 10.4.8 and the current version of MacPorts, rb-mysql fails to compile.

gcc -I. -I. -I/opt/local/lib/ruby/1.8/i686-darwin8.8.1 -I. -DHAVE_MYSQL_SSL_SET -DHAVE_MYSQL_H -I/opt/local/include/mysql5/mysql/ -I/usr/local/include -O -pipe -I/opt/local/include -fno-common -O -pipe -I/opt/local/include  -fno-common -pipe -fno-common  -c mysql.c
mysql.c: In function 'Init_mysql':
mysql.c:2015: error: 'ulong' undeclared (first use in this function)
mysql.c:2015: error: (Each undeclared identifier is reported only once
mysql.c:2015: error: for each function it appears in.)
mysql.c:2015: error: parse error before numeric constant
mysql.c:2018: error: parse error before numeric constant
{standard input}:6318:non-relocatable subtraction expression, "_cMysqlTime" minus "L00000000065$pb"
{standard input}:6318:symbol: "_cMysqlTime" can't be undefined in a subtraction expression
{standard input}:5382:non-relocatable subtraction expression, "_cMysqlRowOffset" minus "L00000000045$pb"
{standard input}:5382:symbol: "_cMysqlRowOffset" can't be undefined in a subtraction expression
{standard input}:5355:non-relocatable subtraction expression, "_cMysqlRowOffset" minus "L00000000044$pb"
{standard input}:5355:symbol: "_cMysqlRowOffset" can't be undefined in a subtraction expression
{standard input}:5333:non-relocatable subtraction expression, "_cMysqlRowOffset" minus "L00000000044$pb"
{standard input}:5333:symbol: "_cMysqlRowOffset" can't be undefined in a subtraction expression
{standard input}:4861:non-relocatable subtraction expression, "_cMysqlTime" minus "L00000000042$pb"
{standard input}:4861:symbol: "_cMysqlTime" can't be undefined in a subtraction expression
{standard input}:4359:non-relocatable subtraction expression, "_cMysqlTime" minus "L00000000041$pb"
{standard input}:4359:symbol: "_cMysqlTime" can't be undefined in a subtraction expression
{standard input}:4106:non-relocatable subtraction expression, "_eMysql" minus "L00000000041$pb"
{standard input}:4106:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:3957:non-relocatable subtraction expression, "_cMysqlTime" minus "L00000000040$pb"
{standard input}:3957:symbol: "_cMysqlTime" can't be undefined in a subtraction expression
{standard input}:3895:non-relocatable subtraction expression, "_eMysql" minus "L00000000040$pb"
{standard input}:3895:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:3824:non-relocatable subtraction expression, "_eMysql" minus "L00000000039$pb"
{standard input}:3824:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:3803:non-relocatable subtraction expression, "_eMysql" minus "L00000000038$pb"
{standard input}:3803:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:3256:non-relocatable subtraction expression, "_cMysqlRowOffset" minus "L00000000023$pb"
{standard input}:3256:symbol: "_cMysqlRowOffset" can't be undefined in a subtraction expression
{standard input}:3226:non-relocatable subtraction expression, "_cMysqlRowOffset" minus "L00000000022$pb"
{standard input}:3226:symbol: "_cMysqlRowOffset" can't be undefined in a subtraction expression
{standard input}:3200:non-relocatable subtraction expression, "_cMysqlRowOffset" minus "L00000000022$pb"
{standard input}:3200:symbol: "_cMysqlRowOffset" can't be undefined in a subtraction expression
{standard input}:2749:non-relocatable subtraction expression, "_eMysql" minus "L00000000019$pb"
{standard input}:2749:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:2595:non-relocatable subtraction expression, "_eMysql" minus "L00000000018$pb"
{standard input}:2595:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:2412:non-relocatable subtraction expression, "_cMysqlStmt" minus "L00000000016$pb"
{standard input}:2412:symbol: "_cMysqlStmt" can't be undefined in a subtraction expression
{standard input}:973:non-relocatable subtraction expression, "_eMysql" minus "L00000000008$pb"
{standard input}:973:symbol: "_eMysql" can't be undefined in a subtraction expression
{standard input}:290:non-relocatable subtraction expression, "_cMysqlField" minus "L00000000004$pb"
{standard input}:290:symbol: "_cMysqlField" can't be undefined in a subtraction expression
{standard input}:232:non-relocatable subtraction expression, "_cMysqlRes" minus "L00000000003$pb"
{standard input}:232:symbol: "_cMysqlRes" can't be undefined in a subtraction expression
{standard input}:190:non-relocatable subtraction expression, "_eMysql" minus "L00000000002$pb"
{standard input}:190:symbol: "_eMysql" can't be undefined in a subtraction expression
make: *** [mysql.o] Error 1

At this point your are either stuck waiting for an update version, or if you are not afraid to dip into the code, you can arm-twist it into working by following these steps:

rb-mysql patch

These steps should be fairly simple to follow:

cd /opt/local/var/db/dports/build/_opt_local_var_db_dports_sources_rsync.rsync.darwinports.org_dpupdate_dports_ruby_rb-mysql/work/mysql-ruby-2.7.1
sudo ruby extconf.rb --with-mysql-include=/opt/local/include/mysql5/mysql/ --with-mysql-lib=/opt/local/lib/mysql5/mysql/
add '#include "my_global.h"' to mysql.c (as the first #include)
sudo make clean
sudo make
sudo make install

And voila. Running the tests will show 3 failing tests, mostly due to imprecisions, but I think you can live with them. Further testing with rails apps did not reveal any problems with MySQL access.

Note: I’ve contacted the maintainer of that port but I have not heard back yet. I will update this post when I do.

A few bonus gems I’ve found helpful, or can’t live without

And since you are in setup mode, you might as well add them to your collection.

sudo gem install acts_as_versioned ajax_scaffold_generator BlueCloth builder fastercsv ferret gettext  htmltools mocha payment radiant  radius rcov rdig RedCloth ruby-debug rubyful_soup selenium shipping
sudo gem install map_by_method what_methods

A new Rails plugin for TextLinkAds (including support for Feedvertising)

Change of Strategy

Instead of updating my constantly breaking Typo sidebar plugin, and to implement Feedvertising from TextLinkAds, I’ve changed gears and chosen to implement just a regular plugin (very close to the new way of doing sidebar plugins in typo 4.1). This approach should work in all versions of typo, as well as any other Ruby on Rails’s application.

The support for feedvertising is slightly different than the one from the WordPress plugin that is the only option offered so far, but should be fairly close.

Installation

Get the plugin from subversion:

script/plugin install http://svn.nanorails.com/plugins/textlinkads/

or to use svn:externals and get future updates via svn update

script/plugin install -x http://svn.nanorails.com/plugins/textlinkads/

The installation will copy a file textlinkads.yml into your config directory.

The file looks like this:

key: TLA_KEY
affiliateid: 0
title: Sponsors
advertisehere: Advertise here!
testing: false
caching: true

Replace TLA_KEY with the one provided by TextLinkAds, set your affiliateid if you’d like to have a link to TextLinkAds with your affiliate id (so you can get credit if someone signs up for a TextLinkAds account). Change the title and advertisehere messages if you don’t like the defaults.

Set testing to false once you’ve verified it works (while testing=true, the plugin will use a special page provided by TextLinkAds that displays to links. However, that page does not contain any RSS links)

Finally, if the caching done by Rails is not enough, the plugin can cache the calls to retrieve the links. See the caching section for explanations on how to setup caching.

Integrating with Typo

Adding the display of regular links

To add the regular TextLinkAds links, you need to add a call to render_TLA anywhere in the rendering code. In typo, the most likely place is in your template’s default.rhtml

Here’s what my template looks like


<div id="sidebar">
  ...
  <div class="sidebar-node"><%= render_TLA %></div>
  <% response.lifetime = 6.hour %>
  <%= render_sidebars %>
</div>

to replace the original:


<div id="sidebar">
  <%= render_sidebars %>
</div>

Add the RSS links

For RSS2.0 for example, edit the file app/views/xml/_rss20_item_article.rxml to add a call to render_TLA_RSS(post_id)

here’s the original file:


  xm.item do
    xm.title post_title(item)
    if this_blog.show_extended_on_rss
      content = item.full_html
    else
      content = item.body_html
    end
    xm.description content
    xm.pubDate pub_date(item.published_at)
    ...

xm.item do
  xm.title post_title(item)
  if this_blog.show_extended_on_rss
    content = item.full_html
  else
    content = item.body_html
  end
  content += render_TLA_RSS(item.id)
  response.lifetime = 6.hour
  xm.description content
  xm.pubDate pub_date(item.published_at)

Depending of which format you need, you may need to edit a different file.

That’s it.

Integrating with other apps

For other apps, just take a similar approach and add calls to render_TLA and render_TLA_RSS where most appropriate. Both calls are accessible from any Controller or Helper class.

Caching

Set “caching: true” in textlinkads.yml. Make sure Rails is configured with some caching. Typically, you need to have


config.action_controller.perform_caching = true
config.action_controller.fragment_cache_store = :file_store, "#{RAILS_ROOT}/tmp/cache"

either set from config/environment.rb or config/environment/[CURRENT ENVIRONMENT].rb

This will cache the pages where the ads appear, and cache the feed pages. But to make sure these pages will update properly if the TextLinkAds ads inventory is updated, you must ensure the cache will expire.

The best way to do that is to use the expiring_cache_action plugin. To install:

script/plugin install http://typosphere.org/trac/browser/trunk/vendor/plugins/expiring_action_cache

Then where you added calls to render_TLA, just add:

response.lifetime = 6.hour

This way, the cached page will expire 6 hours later so that would be the lapse of time to wait to see the updated ads.

No need to expire the cache for RSS, it should get expired automatically every time an article is added.

If you use this plugin in other applications, add a comment or send me a not (psq_0×40_nanorails_0×2e_com) and I’ll add a link to your instructions or code.

Install your own ruby on a shared host

Since I upgraded to Typo 4.0, and in the process rails 1.1.6 I have had a few occurrences where nanoRAILS would hang, several bloated processes would be sitting there and not respond, and the only option at that point was to kill all ruby processes once I realized what was happening, which could be several hours. Suffice it to say, this is not a good option.

So after struggling during last rails upgrade to 1.1 on my host, the next logical step is to also use my own version of ruby so I can have better control on its environment, and even apply patches if necessary.

The following steps apply on a lot of systems. More specifically, my host is DreamHost (aff), and as best I can tell, I’m on a host with Debian Sarge.

Build your own Ruby

Download ruby from http://www.ruby-lang.org. The latest version is currently ftp://ftp.ruby-lang.org/pub/ruby/ruby-1.8.4.tar.gz

Create the makefile using

 ./configure prefix=[YOUR_OWN_RUBY_PREFIX]

Since you most likely don’t have root access, you need to override where ruby think it resides, and the way to do that is to set the prefix to somewhere into your home directory. Something like /home/USERNAME/ruby for example. From that point on, libraries, other builtin ruby files, gems will automatically install into your own ruby repository so you never have to worry about getting in trouble with an unforeseen upgrade.

Optionally, you can apply the patch used by Railsbench, with hardcoded default values because I haven’t figured how to set the environment variables for the dispatch.fcgi process (since apache in my case determines that). Download my version of rubygc.patch .

 patch gc.c rubygc.patch

Build and install ruby

 make
 make install

Additionally, so that the command line uses the same version of ruby, add this to your .bashrc or equivalent for your shel.

export PATH=[YOUR_OWN_RUBY_PREFIX]/bin:$PATH

Install your own gems

Now you are ready to install your own gems. Here’s the bare minimum you need.

First, install rubygems

 wget http://rubyforge.org/frs/download.php/11289/rubygems-0.9.0.tgz
 tar xzvf rubygems-0.9.0.tgz
 cd rubygems-0.9.0
 ruby setup.rb

Then install the minimum set of gems:

 gem install mysql
 gem install fcgi
 gem install rails --include-dependencies

Now, the only thing you need is to change the path to ruby in your dispatch file (dispatch.rb for mod_cgi, dispatch.cgi for regular cgi, and dispatch.fcgi for FastCGI/fcgid)

Typically, replace

#!/usr/bin/env ruby

by

#![YOUR_OWN_RUBY_PREFIX]/bin/ruby

Replace [YOUR_OWN_RUBY_PREFIX] by your own value you used earlier.

Upgraded to Typo 4.0

Well, the upgrade to Typo 4.0 didn’t go so well. No data loss though, so everything’s cool.

At least most pages seem to be functional, so this is not so bad. Combined with having custom sidebar plugins that no longer work, the fact that the merge between the new code and my old one did not quite go as planned, it was not a too pleasant (most of it my own fault I guess).

Anyway, it is getting really late and I’ll finish the rest of the migration tomorrow.

If you tried to access the site while this was going on and you were inconvenienced, pleas accept my most sincere apologies!

If you notice anything weird, please send me a mail at psq _at_ nanorails _dot_ com.

Update, about 20h later, some sleep…: It seems that everything is back up, I migrated my custom plugins to typo 4.0 (about removing 1 file, removing half of the code linked to configuration and adding a few lines) and it seems that everything has been working smoothly :)

And the best of all of that: no more trackback spam! Well, not that it went away, it caught about 25 since last night, but they don’t get published anymore. Just for that, it was all worth it. Thank you everyone in the typo team!

Update 2: Well rails 1.1.5 came out, and it was not enough, so rails 1.1.6 came out and seems to be strong enough to fill in the security issues

And in the process, I also upgraded to Typo 4.0.2

That last upgrade went very smoothly!

However, I’ve had a few annoying cases of nanoRAILS hanging and not responding for hours on hand till I killed the processes. I don’t know yet at this point whether it is due to the new version of rails, the new version of typo, or pehaps some settings that changes on dreamhost. In any case, I’ve installed my own version of ruby and the full set of gems, so we’ll see if that helps!

Rails Documentation Drive

Court3nay from ~:caboose has started a fundraising to be able to pay professional tech writers to beef up the Rails documentation. It is true that it is not advancing quite at the same pace that rails is and Court3nay’s initiative is a worthy one.

He’s aiming to raise $5,000 and after just a few hours he has reached half his goal.

If you enjoy Rails, please consider making a small donation, $10, $20, or whatever you can spare. That’s an investments that is sure to provide a return! So please help.

Fund the Rails Documentation Drive.

Update: the total is now $13,310, from 94 contributors, in less than 24 hours. Thank you everyone that contributed! This is going to help improve the doc a great deal!

RadRails is switching to Ruby-debug

According to Kyle, one of the tireless developer of Rad Rails, he is working on incorporating ruby-debug.

For more details about ruby-debug, see my write up about it.

The command line is great, and there are times when you are working on a remote server where nothing else will do. But having the ability to set breakpoints at the click of the mouse, see your variables in a separate pane, see a lot more of your source code is something quite convenient.

And with the added speed of ruby-debug, this should make debugging in Rad Rails something you can’t afford not to use.

This is very welcome news and I look forward to use it!

A better Rails debugger: ruby-debug

Just a few days ago, Kent Sibilev quietly released an amazing little plugin with far reaching consequences: ruby-debug. This is a marked improvement over Ruby’s own rdebug. The major difference is that he removed the major slow down that impacted rdebug usability with Ruby on Rails so it is blazing fast.

Instead of using the Kernel#set_trace_func API, which makes it possible to implement a debugger in Ruby, but has a negative effect on the speed on your program execution, he uses a native extension with a new hook using the Ruby C API

For each trace call Ruby interpreter creates a Binding object, even though it is not being used most of the time. ruby-debug library moves most of the functionality of debug.rb to a native extension, this way significantly improving the execution of your program.

This means that watchpoints and the standard tracing facility are not supported, but I’m gladly giving that up for the comfort and speed. And if you are wondering how the speed is, that is really the difference between utter frustration each time you debug something to bliss!

Previously I covered some options for Debugging in Rails. This is going to become my preferred option by far, and I’m willing to bet this will become yours too. Why? Because you can see the source code of where you are, you can execute step while watching some or your variables, you can inspect of your variables (this you could do with breakpointer), you can use conditional breakpoints, you can get a list of expressions to be displayed every time you step. The downside compared to breakpointer? You can’t do it remotely, which in most instances, as best as I can tell, is not going to be a problem at all.

Installation

Ruby-debug comes as a gem so to install, just run:

sudo gem install ruby-debug

Make sure you chose the proper windows or ruby version depending on your platform.

Using ruby-debug

To use in your rails application, assuming you want this to only be available in development mode (this is not such a great idea to leave in in production mode, just in case you forget to remove the breakpoints, and also for performance reasons as I’ll explain in a bit)

In environement.rb add the following:

SCRIPT_LINES__ = {} if ENV['RAILS_ENV'] == 'development'

This line is important if you want to be able to see your source code. SCRIPT_LINES__ is an obscure feature of the ruby interpreter. If it is defined, it will store all loaded ruby file in a hash, which debug-ruby will use to display where you are in your source code. The only problem is that it can have some impact on performance, and worst of all, use up quite a bit of memory, which is not so good in production (hence the “if ENV[‘RAILS_ENV’] == ‘development'”). SCRIPT_LINES__ needs to be initialized as early as possible so it can capture all loaded ruby files.

To add a breakpoint, you will need to use:

require 'ruby-debug'
...
def your_method
  ...
  debugger if ENV['RAILS_ENV] == 'development'
  ...
end

Then start your app using webrick (it does not work with lighttpd and I have not investigated why just yet):

script/server webrick

When the code hits the breakpoint, you are in a console like mode (not unlike irb or script/console).

Ruby-debug commands

  • b[reak]
    list breakpoints
  • b[reak] [file|class:]LINE|METHOD [if expr]
  • b[reak] [class.]LINE|METHOD [if expr]
    set breakpoint to some position, optionally if expr == true
  • cat[ch]
    show catchpoint
  • cat[ch] EXCEPTION
    set catchpoint to an exception
  • disp[lay] EXPRESSION
    add expression into display expression list
  • undisp[lay][ nnn]
    delete one particular or all display expressions if no expression number given
  • del[ete][ nnn]
    delete some or all breakpoints (get the number using “break”)
  • c[ont]
    run until program ends or hit breakpoint
  • r[un]
    alias for cont
  • s[tep][ nnn]
    step (into methods) one line or till line nnn
  • n[ext][ nnn]
    go over one line or till line nnn
  • w[here]
    displays stack
  • f[rame]
    alias for where
  • l[ist][ (-|nn-mm)]
    list program, – list backwards, nn-mm list given lines. No arguments keeps listing
  • up[ nn]
    move to higher frame
  • down[ nn]
    move to lower frame
  • fin[ish]
    return to outer frame
  • q[uit]
    exit from debugger
  • v[ar] g[lobal]
    show global variables
  • v[ar] l[ocal]
    show local variables
  • v[ar] i[nstance] OBJECT
    show instance variables of object
  • v[ar] c[onst] OBJECT
    show constants of object
  • m[ethod] i[nstance] OBJECT
    show methods of object
  • m[ethod] CLASS|MODULE
    show instance methods of class or module
  • th[read] l[ist]
    list all threads
  • th[read] c[ur[rent]]
    show current thread
  • th[read] [sw[itch]] nnn
    switch thread context to nnn
  • th[read] stop nnn
    stop thread nnn
  • th[read] resume nnn
    resume thread nnn
  • p EXPRESSION
    evaluate expression and print its value
  • pp EXPRESSSION
    evaluate expression and print its value
  • h[elp]
    print this help
  • RETURN KEY
    redo previous command. Convenient when using list, step, next, up, down,
  • EVERYHTING ELSE
    evaluate

Happy debugging!

Installing Rails on Mac OS X Tiger

2/23/07 update: some things have changed since I wrote this page, either in MacOS itself, or the components referenced. So before you start, be sure to also check a recent update for 10.4.8 and the comments of both pages that contain some valuable information.
If something still does not work, please leave a comment and someone will help you.

I recently Switched back to a Mac, while other long time Mac users are switching to Linux. And I love every minute of it! Once I got the basic stuff going, it was time to install a fitting Ruby on Rails environment on my new iMac.

There are a number of approaches you can use (see the reference section at the bottom). I was after installing an environment as close as one you can use in production, but right here on my desk.

If you are only looking for the basics, Locomotive is probably what you need, if you want a grown-up rails setup on Mac OS Tiger, read on.

Choosing an install method

There are 3 approaches to installing Ruby on Rails on Mac OS Tiger.

You can use the one click approach, and Locomotive is probably the simplest. My main issue is that it is a bit too opaque and if you want to patch anything, upgrade one one the component, you might be out of luck.

You can use the “compile everything from source approach”, and Hivelogic covers this well. This is an approach you might prefer except that you may run into Mac specific issues not covered by typical Unix/Linux code

A third option is to rely on Darwin ports as covered by Evan with “a better way of building ruby, rails, lighttpd, mysql, and postgres on OS X tiger

This third method gets my vote: less opaque, but a large number of smart and dedicated people have already worked out all the problems.

So with that covered, let’s get on with that “grow-up setup” (thanks Coda!). Hmm OK, just one last word of warning before you begin. I’ve installed more than the bare minimum. If you follow these directions, you’ll be all set for standalone lighttpd , standalone mongrel, apache, rails with mongrel and a few more combinations. I haven’t got to using pound just yet, so we’ll keep this for some other time.

Installation on Tiger

If you have not installed Darwin port, now is the time.
Then update port itself

sudo port -d selfupdate

Fix the root path and set the PATH variable in /etc/profile. You may not need this is you are not going to run things as root. Although this will simplify a few things for you.

mate /etc/profile    #fill free to use vi or any other editor you&#8217;d like
PATH=&#8221;/opt/local/bin:/opt/local/sbin:/bin:/sbin:/usr/bin:/usr/sbin&#8221;

Install Apache 2

sudo port install apache2

Create a default configuration for apache

cd /opt/local/apache2/conf
cp httpd.conf.sample httpd.conf

Start Apache

sudo launchctl load -w /Library/LaunchDaemons/org.darwinports.apache2.plist

Rebooting would do the trick too. At this point you should have a “It works!” if you point a browser to http://localhost

Install fcgi (not really going to use it, so it is a just in case so I can benchmark it at some point)

sudo port install fcgi

Install lighttpd

sudo port install lighttpd +ssl

Install mysql 5

sudo port install mysql5 +server

start mysql 5 (you can also reboot)

sudo launchctl load -w /Library/LaunchDaemons/org.darwinports.mysql5.plist

Change the mysql root password (on localhost AND on your network card)

/opt/local/lib/mysql5/bin/mysqladmin -u root password &#8216;new-password&#8217;
/opt/local/lib/mysql5/bin/mysqladmin -u root -h [HOSTNAME] password &#8216;new-password&#8217;

Check it works (empty password if you have not set it)

mysql5 -u root -p

Install subversion

sudo port install subversion +mod_dav_svn +tools

Install ruby and a few goodies

#ruby
sudo port install ruby
sudo port install rb-rubygems
sudo port install rb-termios
sudo port install rb-fcgi
sudo port install rb-mysql5
sudo port install imagemagick

Install Apache mod_fcgi module

sudo port install mod_fastcgi

add the following line to /opt/local/apache2/conf/httpd.conf

LoadModule fastcgi_module modules/mod_fastcgi.so&#8221;

Install gems you can’t live without

sudo gem install -y rake
sudo gem install -y rails
sudo gem install -y capistrano
sudo gem install daemons gem_plugin mongrel mongrel_cluster &#8211;include-dependencies
sudo gem install rmagick

One good gem to have would be sendfile to avoid copying data between apache and mongrel for example, but the Tiger kernel does not support it despite having the function defined in the C header files. So since it is not really a production machine, we can live without it.

At this point, you’ve got more that the basic setup for Ruby on Rails. That was no too bad, wasn’t it? Although arguably, this could be easier!

Deploying a rails application: Mephisto

For good measure, just to check that our setup is all good, let’s install Mephisto. The latest Rails blog engine.

Create the databases

mysqladmin5 -u root create mephisto_development
mysqladmin5 -u root create mephisto_test
mysqladmin5 -u root create mephisto_production

Checkout everything

svn co http://svn.techno-weenie.net/projects/mephisto/trunk mephisto

Configure the database (should be the right default)

cd mephisto/config
cp database.example.yml database.yml
mate database.example #to check that the database name are what we created

Populate the database

rake RAILS_ENV=production db:bootstrap

And start. Since lighttpd is installed, that’s what it is using

script/server

Point your browser to http://localhost:3000 and yes! It works :D
Or you can go to http://localhost:3000/admin (using admin/test for user/password)

Now let’s finish our “grown up setup” and configure mongrel cluster

mongrel_rails cluster::configure -e production -p 8000 -a 127.0.0.1 -N3 -c [RAILS_ROOT of mephisto]

a few note on Capistrano

My initial Capistano Cheat Sheet should be enough with one exception. SSH is not enabled by default on Tiger. To enable, use the “Sharing” panel under System Preferences and enable “Remote Login”.

And second, if you have trouble when running via ssh, you may need to fix ssh PATH. To do that, create a file under ~/.ssh/environment with:

PATH=/opt/local/bin:/opt/local/sbin:/opt/local/apache2/bin:/bin:/sbin:/usr/bin:/usr/sbin

Run Mongrel Cluster as a service

Now let’s configure Mongrel Cluster to start at boot time

sudo mkdir /etc/mongrel_cluster
ln -s [YOUR RAILS_ROOT]/config/mongrel_cluster.yml /etc/mongrel_cluster/[your application].yml

Create a file ~/Library/LaunchAgents/mongrel_cluster.plist

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
        <key>Debug</key>
        <true/>
        <key>Label</key>
        <string>org.rails.mongrel.cluster</string>
        <key>OnDemand</key>
        <false/>
        <key>Program</key>
        <string>/opt/local/bin/daemondo</string>
        <key>ProgramArguments</key>
        <array>
                <string>&#8211;label=mongrel_cluster</string>
                <string>&#8211;start-cmd</string>
                <string>/opt/local/bin/mongrel_cluster_ctl</string>
                <string>start</string>
                <string>-v</string>
                <string>-c</string>
                <string>/etc/mongrel_cluster/</string>
                <string>;</string>
                <string>&#8211;stop-cmd</string>
                <string>/opt/local/bin/mongrel_cluster_ctl</string>
                <string>stop</string>
                <string>-v</string>
                <string>-c</string>
                <string>/etc/mongrel_cluster/</string>
                <string>;</string>
                <string>&#8211;restart-cmd</string>
                <string>/opt/local/bin/mongrel_cluster_ctl</string>
                <string>restart</string>
                <string>-v</string>
                <string>-c</string>
                <string>/etc/mongrel_cluster/</string>
                <string>;</string>
                <string>&#8211;pid=none</string>
        </array>
        <key>RunAtLoad</key>
        <true/>
        <key>StandardErrorPath</key>
        <string>/tmp/mongrel.log</string>
        <key>StandardOutPath</key>
        <string>/tmp/mongrel.log</string>
</dict>
</plist>

Additionally, if you did not want to modify /etc/profile, you can add:

    <key>EnvironmentVariables</key>
    <dict>
        <key>PATH</key><string>/opt/local/bin:/opt/local/sbin:/bin:/sbin:/usr/bin:/usr/sbin</string>
    </dict>

And finally, you can start mongrel cluster. or logging in will work:

sudo launchctl load -w ~/Library/LaunchAgents/mongrel_cluster.plist

To have it work at boot time, you will need to put mongrel_cluster.plist under /Library/LaunchDaemons instead.

References

lighttpd

http://duncandavidson.com/essay/2005/12/railsonlighty
http://duncandavidson.com/essay/2006/01/railsvhostingonlighty

Rails installation

rails with postgres on tiger using Darwin Ports
Lighttpd with rails on tiger
Time For A Grown-Up Server: Rails, Mongrel, Apache, Capistrano and You
Rails installation from single script
Locomotive, one click rails installer for Mac OS X

pound

pound + lighttpd + mongrel

10/17/06 update: I’ve reinstalled on a brand new system with Mac OS 10.4.8. See my notes on what has changed.

textmate rails cheat sheets

I’m just discovering TextMate and I have to say I’m impressed! For those of you who don’t know me, it takes quite a bit for me to admit that I’m impressed.

Over the years, I’ve used quite a few editors, and I happen to think that vi is one the greatest. Hmmm, I can see some eyebrows perking up, and most of you starting to think that I’m weird, either because you’ve never heard of vi, or because you’ve learned to hate it. But I like it because it is dead simple (once you are over the initial learning curve), has powerful regexp, and gets the job done. And once you’ve learned it, that is the kind of thing you don’t forget. I’ve liked emacs at some point, but it is way too heavy, and after a few years of not using it, you’ve got to learn it all over again, but I digress…

Back to TextMate. I’ve not used it much yet, but I love the concepts. Lots of keyboard action (the mouse is great, but going back and forth between mouse and keyboard can be a drag (pun intended!)). And it has very powerful macros that look easy to customize. Give me more!

So I went out I looked for quick ways to get started. I found a couple of interesting cheat sheet that I’d like to share with you. If you know of any other, please let me know!

The first rails textmate cheat sheet is by Sebastien Friedrich and documents the snippets (a.k.a. tab triggers) from the TexMate Rails Bundle (by syncPEOPLE. (via O’Reilly Ruby)

The second is TextMate Cheat Sheet for Rails Hackers is provided by Pragmatic Studio and includes some of the same information, plus some more general textmate shortcuts useful with Rails (via Tim Kuntz).

The third is TEXTMATE cheat sheet and is a more general purpose guide to the shortcuts of TextMate. (via macromates).

And while I’m on the subject of Cheat Sheet, here are 2 bonus rails and ruby Cheat Sheets:

With all 5, you should be all set!

TextLinkAds Typo Sidebar Plugin

Based on “Displaying ads from TextLinkAds in a rails application”, here’s the first release of my typo sidebar plugin to display ads from TextLinkAds. The plugin uses typo built-in caching as I explained before.

Download

Download either textlinkadssidebar.zip or textlinkadssidebar.tgz.

Installation

Unzip (unzip textlinkadssidebar.zip) or untar (tar xzvf textlinkadssidebar.tgz) directly into the components/sidebars/ directory of your typo installation.

Configuration

Using the sidebar tab of the admin section of typo, you’ll find an Item named “Text-Link-Ads” on the left hand side.
Simply drag it to the right side where at the desired location (the higher the better!).
Enter a title for that section (here I use nanoRAILS Sponsors).
Fill in your XML KEY from the “Get ad code” section on TextLinkAds.
Enter your affiliate ID (so you can get paid for referrals).
Enter the text for the referral link (I have “Advertise on nanoRails”).
Click on the Publish Changes button.
Once you refresh your blog, you will have a TextLinkAds section.

Text Link Ads

6/15/06 update: to use in the trunk of typo (1055 currently), you will need textlinkadssidebar-1055.zip or textlinkadssidebar-1055.tgz.

The short of it is that sidebar plugins have changed quite a bit! You may be better off recreating from scratch using one of the available ones.

The longer story is that you no longer need a configure.rhtml. Instead, you use the setting helper to describe each setting. You need to subclass Sidebars::ComponentPlugin instead of Sidebars::Plugin. You also need to remove the configure method and the way you specify the display name and and the description is also done with a helper.

Oh yeah, the file content.rhtml is unchanged :D