Help us understand the problem. What is going on with this article?

whereにSQLの文字列を渡したくない!

なんで文字列を渡したくないのか

  • なんとなく文字列で渡すというのが地に足がついてない感じでイヤ
  • DBの種類を変えると動かなくなる可能性がある
  • mergeができないことがある

例えばこんなの書きたくない

比較演算

target_age = 30
User.where('age >= ?', target_age)

or

target_name1 = '山田'
target_name2 = '田中'
User.where('name=? OR name=?', target_name1, target_name2)

like

target_letter = '田'
User.where('name like ?', "%#{target_letter}%")

Arel::tableを使う

ActiveRecordは内部でArelというSQL生成用ライブラリを使用している。
直接使うこともできるので、Arelで作ったSQLを文字列の代わりにwhereに渡してやろう、ということ。

比較演算

target_age = 30
User.where(User.arel_table[:age].gt(target_age))

ちなみに、
* = (equal) : eq
* < (less than) : lt
* <= (less than equal) : lteq
* > (greater than) : gt
* >= (greater than equal) : gteq

or

target_name1 = '山田'
target_name2 = '田中'
User.where(User.arel_table[:name].eq(target_name1).or(User.arel_table[:name].eq(target_name2)))

like

target_letter = '田'
User.where(User.arel_table[:name].matches("%#{target_letter}%"))

Squeelを使えばもっといい感じに!

Arel::tableでもとりあえず当初の目的は達成できたけど、如何せん長い…
Gemを入れてよければ、Squeelを使えばスッキリ書ける。

比較演算

target_age = 30
User.where{age >= target_age}

()ではなく{}を使う。

or

target_name1 = '山田'
target_name2 = '田中'
User.where{(name == target_name1) | (name == target_name2)}

||ではなく|
ちなみにandも&&ではなく&

like

target_letter = '田'
User.where{name =~ "%#{target_letter}%"}

これだけ見るとSqueelの完全勝利に見えるけど、
Arel::tableだとSQLの生成式を関数化して、複数箇所で使いまわせたりして便利だったりするのかな。

参考

ActiveRecord4でこんなSQLクエリどう書くの? Arel編
ActiveRecord4でこんなSQLクエリどう書くの? Squeel編

activerecord-hackery/squeel

Kta-M
fusic
個性をかき集めて、驚きの角度から世の中をアップデートしつづける。
https://fusic.co.jp/
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした