ActiveRecordに苦戦しながらテーブル結合したりしてデータ取得した話です。
背景
Rails初心者がデータの更新や、複数テーブル、複数条件で指定する時があるかと思います。
今回はその時に調べたことを簡単にまとめていますので、興味がある方は是非。
なので、今回はRails初心者向けの内容ですね。
結論
まずはテーブルの結合、条件指定のやり方
TableA.joins(:table_b)
.where(:table_b {id: 1})
.where(id: 1)
joinsで内部結合しつつ、そのテーブルで条件を指定しています。
.where().where()でAND条件になっています。
そして、条件でorを使用するパターン
今回はvalueの範囲指定をorで繋げます。
TableA
.where(foreign_id: 1)
.where('value >= ?', 0)
.or(TableA.where(foreign_id: 2 ).where(value: 0..100))
.order(:sort)
foreign_idが1で、valueが0以上のデータと、
foregin_idが2でvalueが0以上100以下のデータを取得します。
以下は.whereで取得したRerationに対して更新しています。
relation.each do |data|
# ここでdataの値を変更する
data.save!
end
こうして変更したいデータ群の抽出と、それらのデータ更新を行いました。
何が大変だったか
ActiveRecordを使いながら知っていくのが大変でした。
.where()などを使うとrerationが返却されてきているので、.firstや.each()などを使用しないと例え1件しか取得していなくてもデータアクセスができません。それに、.load()を明示的に呼ばない限りはまだqueryを発行していないこともありますので、logger.debugの出力タイミングが意図しない順番になったりなど知っていないと難しい部分がありました。
基本だとは思いますが、クラスを調べれば大体なんとかなります。今回で言えばRelationクラスについて調べることで基本的に解決できました。
今後も複雑な条件が必要になってきたりすると思うのですが、その度に調べることになりそうです。
楽しみつつのRailsとの格闘はまだまだ続きそうです。