😎

Ruby on RailsのWhereのプレースホルダは%記法での式展開ができる

2023/08/28に公開

Rails7以上でMySQLでWhere文の条件を文字列以外で展開してほしい場合に利用しました。
例えば、ユーザーの生年月日から現在の月が誕生日のユーザーを絞り込むクエリで利用しました。

User.where("DATE_FORMAT(`birthday`, '%s') = %i", '%m', Time.now.month)

もともとのコードは下記だったのですが、Rails7にしたときにこのクエリだと意図した結果が得られなくなってしまいました。

User.where("DATE_FORMAT(`birthday`, '%m') = ?", Time.now.month)

なぜ気づいたのか?

Rails7にバージョンアップする際に、?プレースホルダを展開する際に必ず'(クオート)で囲まれてしまうそうです。
これまではそうではなかったようでした。このことによって?プレースホルダで展開された結果が文字列として認識されてしまうため、
一部クエリの結果が意図しないものになってしまう問題が、Rails6.1 -> 7.0の過程で発生しました。
そして、対応方法を調べていく中でその一つとして、%記法の式の展開がわかったのでした。

sanitize_sql_array(["name='%s' and group_id='%s'", "foo'bar", 4])
# => "name='foo''bar' and group_id='4'"

この%記法はいつから使えるのか?

なんとこの記法はRails7で導入されたわけではなく、3.1くらいの時から利用できるようでした。うーん、Rails奥が深いですね。

さいごに

弊社ではRuby on Railsのアプリケーションを6年以上運用していますが、定期的にバージョンアップを行っております。
現状の最新版であるRails7.0を利用しているので、ある程度胸張って、サーバーサイドはモダンな環境であると言えるようになってきたので、もしモダンなRailsを扱うWebアプリケーションに興味がある方はこちらからご応募ください!

OSIRO テックブログ

Discussion