開発備忘録 2018/10/24
MySQL で SELECT の結果に対して UPDATE を適用する
status
が temp
のレコードを全て active
にする。
UPDATE users, ( SELECT users.id FROM users WHERE status = 0 # 0: temp, 1: active, 2: leaved ) AS temp_users SET users.status = 1 WHERE users.id = temp_users.id
FactoryGirl の transient について
FactoryGirl において一時的な attribute を定義することができる。
transient で定義した attribute はモデルを build (create) した際にセットされることはなく、また attribute_for
で attribute を取り出すときには無視される。
何のためにこの機能が提供されているかというと DRY に書くためである。
例えば、以下の FactoryGirl のコードを DRY にする方法について考えてみる。
factory :character do name { "Jack (job)" } trait(:knight) do name { "Jack (knight)" } end trait(:fighter) do name { "Jack (fighter)" } end trait(:wizard) do name { "Jack (wizard)" } end end
job
に応じて name
の表記が微妙に変わるというものだが、今回の場合だと name { "Jack" }
の部分が重複していて DRY ではない。
これが transient を使うとこう書ける。
factory :character do transient do job "job" end name { "Jack (#{job})" } trait(:knight) do job "knight" end trait(:fighter) do job "fighter" end trait(:wizard) do job "wizard" end end
job
を transient に定義しておいて、trait で job
の値を更新するというわけだ。
ちなみに job
の値を外から渡したい場合はこう書く。
create(:character, job: 'thief')
また callback で transient を利用したい場合は第二引数が transient なのでそれを利用する。
factory :character do ... after(:create) do |character, evaluator| character.name += " #{evaluator.job}" end end