49hack

見習いエンジニアが魔法使いになるまで

rails4のenumはupdate_allで使うときは注意が必要

Rails4.1.0から使えるようになったenumがめちゃめちゃ便利です。

例えばUserモデルにstatusというINTのカラムがある場合、enumを使うと直感的に管理できるようになります。

class User < ActiveRecord::Base
  # ステータス: temporary (仮登録), active (本登録), resign (退会).
  enum status: %i(temporary active resign) 
end

この場合は自動的にtemporary: 0, active: 1, resign: 2になります。

値を自分で設定したい場合はハッシュで定義すればOKです。

class User < ActiveRecord::Base
  # ステータス: temporary (仮登録), active (本登録), resign (退会).
  enum status: {temporary: 10, active: 20, resign: 30} 
end

詳しい使い方は参考URLを参照。

いろいろと便利なenumですが、今回問題なのが更新するところ。

# status を 2 (resign) に変更
user.resign!

# status を 1 (active) に変更
user.update(status: :active)

# status を 1 (active) に変更
users = User.all
users.update_all(status: :active)
# => ERROR

update_allはローレベルAPIなので、enumの処理ができません。。なので値をちゃんと渡してあげる必要があります。

# status を 1 (active) に変更
users = User.all
users.update_all(status: User.statuses[:active])

以上です。

参考