RailsをHackする

Railsの基本理念は"DRY(同じことを繰り返さない)"。

でもよく考えると自分は新しいアプリケーションを作る度に毎回、$KCODE='u'を追記したり、database.ymlを修正したり、と言う作業を繰り返してることに気づきました。

というわけで、RailsをHackしてここらへんの作業を自動化してみます。

文字コードの設定

文字コードの設定を記述する、config/environment.rbはアプリケーションを作成する際に実行するrailsコマンドで作成されるファイルですが、これは$RAILS/environments/environment.rb($RAILSRailsのインストールディレクト*1 )をテンプレートとして作成されます。

つまりこのファイルに以下のように$KCODE='u'と追記しておけば、以降railsコマンドで作成されるアプリケーションは既にUTF-8対応の設定がされている状態になります。

# Be sure to restart your web server when you modify this file.
$KCODE = 'u'

# Uncomment below to force Rails into production mode when
# you don't control web/app server and can't set it the proper way
# ENV['RAILS_ENV'] ||= 'production'

# Specifies gem version of Rails to use when vendor/rails is not present
<%= '# ' if freeze %>RAILS_GEM_VERSION = '<%= Rails::VERSION::STRING %>'

データベースの設定

次はデータベースの設定。

自分はいつもsqlite3をデータベースとして使用するのですが、普通にrailsコマンドを実行するとMySQL用の設定ファイルが作成されます。これはコマンド実行時に

 $ rails -d sqlite3 <アプリケーション名>

と指定してすることで変えることも出来ますが、いちいちオプションを指定するのも面倒なのでsqlite3をデフォルトで使用するようにrailsコマンドの動作を変えてみます。

railsコマンドの動作は、$RAILS/lib/rails_generator/generators/applications/app/app_generator.rbに記述されており、デフォルトで使用するデータベースもその中で指定されています。

class AppGenerator < Rails::Generator::Base
  DEFAULT_SHEBANG = File.join(Config::CONFIG['bindir'],
                              Config::CONFIG['ruby_install_name'])

  DATABASES = %w( mysql oracle postgresql sqlite2 sqlite3 )

  default_options   :db => "mysql", :shebang => DEFAULT_SHEBANG, :freeze => false

ここのdefault_optionsの行を

  default_options   :db => "sqlite3", :shebang => DEFAULT_SHEBANG, :freeze => false

と変えてやると、デフォルトのデータベースにsqlite3が使用されるようになります。

なお、データベース設定ファイルのテンプレートは、$RAILS/configs/databases/ディレクトリの下に配置されています。

もう少し凝ったこと、例えばdevelopmentにはsqlite3、testとproductionにはMySQLを使用したい場合は、

development:
  adapter: sqlite3
  database: db/<%= app_name %>_development.sqlite3

test:
  adapter: mysql
  database: <%= app_name %>_test
  username: root
  password:
<% if socket -%>
  socket: <%= socket %>
<% else -%>
  host: localhost
<% end -%>

production:
  adapter: mysql
  database: <%= app_name %>_production
  username: root
  password:
<% if socket -%>
  socket: <%= socket %>
<% else -%>
  host: localhost
<% end -%>

という内容で、$RAILS/configs/databases/default.ymlというファイルを作ってやり、app_generator.rb

  DATABASES = %w( mysql oracle postgresql sqlite2 sqlite3 default )

  default_options   :db => "default", :shebang => DEFAULT_SHEBANG, :freeze => false

と変更することで実現できます。

注意点

ここに書いた内容は、Railsそのものを書き換えるという泥臭い*2Hackなので、正直なところあまりお薦めできる方法ではないです。バージョンアップした際には、また書き直す必要がありますし。まあでもこんなやり方もあるということで。

*1:自分の環境だと/usr/lib/ruby/gems/1.8/gems/rails-$version

*2:generatorを自作したほうがスマートかも?