Rails1.2.3 + mongrelで一つのホストに複数のアプリを同居させるときに気をつけること

SSL証明書は結構高いので、あるアプリ内のユーザー入力フォームと別ポートで立てているバックエンドの管理システムを一つのホストに同居させたいケースがあると思います。たとえば本サイトは3001番、管理システムは3002番ポートで起動していて、

  • 本サイト:http://hoge.com/
  • 申込画面:http://hoge.com/apply
  • 管理画面:http://hoge.com/admin

というように運用したいケースです。
mongrelには--prefixという便利なオプションが付いているので、管理システム起動時に


mongrel_rails start -e production -p 3002 -d --prefix /admin
と指定してやり、あとはフロントで/adminを3002番ポートに振り分けてやるだけでよいです。ちなみにフロントがApache2でmod_proxyを利用するケースだと、confファイルで

ProxyPass /admin http://localhost:3002/
ProxyPassReverse /admin http://localhost:3002/
という感じです。
ここで一つ問題となるのはview内で指定しているパス。例えば"rails-app/public/css/common.css"を読むために


と書かれているとアウトです。上記ケースでの正解は


ただしこれは、いかにもなんだかなぁという感じですね。パスがadmin固定になるので可搬性がなくなってしまいます。
解決策の一つとして絶対パスをやめて相対パスを指定してやるという方法があります。ただ、階層が深くなると"../../../css/common.css"みたいな感じであまり美しくないので、できれば避けたい気もします。そこでrailsの便利なヘルパーを利用します。

<%= stylesheet_link_tag "scaffold", "/common/css/site.css" %>
このように書いてやることで、実行時には


と自動的にprefixつきアドレスに変換してくれます。キャッシュ対策に乱数付与のおまけつきです。sytlesheet以外でも、以下のメソッドで同じようにprefixを付けてくれることを確認しています。

  • javascript_include_tag
  • image_path
  • url_for
  • form_tag
  • link_to_remote

他の類似メソッドでもおそらく大丈夫でしょう。view内のパス指定には必ずhelperを用いるようにすることで、アプリケーションのポータビリティを簡単に実現できるわけです。
ただ、静的htmlやcss内で指定されたパスには適用できないので、そちらについては絶対パスでなく相対パスを指定してやるように心がければよいでしょう。