Ruby on RailsにおけるMigrationについて

こんばんは、south37です。
2回のruby回を経て、ようやくrailsに戻って参りました。
初回ではmodelについて簡単に説明した訳ですが、今回はmodelと密接に関連するmigrationというものについて説明したいと思います。

migrationとは

migrationとは、データベースのテーブル生成やカラム追加なんかを管理する為の機構です。Ruby on Rails(というかその中のツールの一つであるActiveRecord)においては、独自のDSLでmigrationファイルというものを書き、rake db:migrateというコマンドを実行する事でそのmigrationファイルの定義に従ったテーブルが作られます。migrationファイルを共有しておけば全く同じテーブルをどの環境でも用意出来ますので、例えば開発環境と本番環境でテーブル定義を揃えたい場合なんかに使えますね。

ActiveRecord

modelやmigrationはActiveRecordの機能の一つになっています。ActiveRecordというのはいわゆるORMで、RDBをラップして使いやすいインターフェースを提供してくれます。例えば、modelのメソッドを呼び出す際やmigrationを実行する際にはSQLを書く必要はなく、ActiveRecordの側でデータベースの差異というのは吸収してくれます。その為、開発環境ではsqlite3で本番環境ではpostgresqlといった事も簡単に出来ます。
modelのコードは前回見せたので、migrationファイルというのがいったいどういったものなのか見てみましょう。

class CreateUsers < ActiveRecord::Migration
  def change
    create_table :users do |t|
      t.integer :foursq_id
      t.float :area

      t.timestamps
    end
  end
end

がuserテーブル生成用のmigrationファイルです。changeって名前のメソッドになってるのは、up(テーブル生成)もdown(テーブルdrop)も出来るって事です。upメソッドとdownメソッドを分けて書く事も出来ます。
create_tableメソッドにテーブル名のシンボルとブロックを渡します。ブロックの中ではt.~って形でカラムを定義します。idは自動で振られて、さらにt.timestampsでcreated_atカラムとupdated_atカラムが作られます。これでさくっとテーブルが完成です。
後からテーブル定義を更新する場合には、migrationファイルを追加していきます。例えば、カラムを増やしたい時は、

class AddColumnNameToUsers < ActiveRecord::Migration
  def change
    add_column :users, :name, :string
  end
end

みたいな感じで書きます。add_columnの第一引数にテーブル名のシンボル、第二引数にカラム名、第三引数に型情報が入ってます。後からの変更も用意に出来るのがとても便利です。

リレーショナルなテーブル

リレーショナルなテーブルも簡単に作れます。例えば、userに紐づいたterritoryのテーブルは、

class CreateTerritories < ActiveRecord::Migration
  def change
    create_table :territories do |t|
      t.float :lat
      t.float :lng
      t.string :name
      t.integer :been_here
      t.string :venue_id
      t.references :user

      t.timestamps
    end
    add_index :territories, :user_id
  end
end

みたいな感じで書きます。特に注目して欲しいのはt.referencesって書いてるとこで、ここでuserを指定している事でuser_idカラムを生成します。referencesって書いちゃうのがかっこいいですね

rails generateコマンド

ここまで書いたmigrationファイル、SQL書くよりは書き易そうと言っても自分で書くのは面倒ですよね。実は、railsではmigrationファイルとmodelを自動で生成してくれるrails generate modelコマンドがあります。例えば、rails generate model user foursq_id:string area:floatってコマンドを叩くと、userモデルが作られ、さらに最初の例でのせたのと同様のmigrationファイルが作られます。後は、rake db:migrateをすればテーブルが出来あがり、modelも自由に使えるようになります。
このように、ファイルをもりもり自動生成してくれるのも、railsの大きな特徴です。実際にサービスが動く様子が見れるところまで圧倒的に短い時間で辿り付けるので、とても便利です。