設定しているときに無視したいという特殊なケースの対策。基本は打ち消しをしないことを前提に書いたほうがよいが書かざるを得ないときにどうするかのためのメモ。
環境
$ bin/rails -v Rails 7.1.2
前提
has_manyなどの子の関連に関して、デフォルトの並び順を設定することができる。詳しくは以下の記事を参照のこと。
RailsのActiveRecordのhas_manyにはorderで順番の指定できる - コード日進月歩
例
例えば以下のようなModelがあったとする
# == Schema Information # # Table name: soccer_teams # # id :bigint not null, primary key # name :string(255) # created_at :datetime not null # updated_at :datetime not null # class SoccerTeam < ApplicationRecord has_many :soccer_member, -> { order(:name) } end
# == Schema Information # # Table name: soccer_members # # id :bigint not null, primary key # name :string(255) # soccer_team_id :bigint not null # created_at :datetime not null # updated_at :datetime not null # class SoccerMember < ApplicationRecord belongs_to :soccer_team end
普通に SoccerTeam
がhas_manyで持っている SoccerMember
を取得しようとすると以下のようになる。
SoccerTeam.first.soccer_member.to_sql # "SELECT `soccer_members`.* FROM `soccer_members` WHERE `soccer_members`.`soccer_team_id` = 5 ORDER BY `soccer_members`.`name` ASC"
例えばこれをid順にしたいと思ったときに下記のようにしても、nameのorderが優先されてしまう
SoccerTeam.first.soccer_member.order(:id).to_sql # "SELECT `soccer_members`.* FROM `soccer_members` WHERE `soccer_members`.`soccer_team_id` = 5 ORDER BY `soccer_members`.`name` ASC, `soccer_members`.`id` ASC"
これを回避するためには reorder
を利用する。
SoccerTeam.first.soccer_member.reorder(:id).to_sql "SELECT `soccer_members`.* FROM `soccer_members` WHERE `soccer_members`.`soccer_team_id` = 5 ORDER BY `soccer_members`.`id` ASC"