[解決済み] Railsのhas_manyリレーションでデフォルトでスコープを使用する
質問
次のようなクラスがあるとします。
class SolarSystem < ActiveRecord::Base
has_many :planets
end
class Planet < ActiveRecord::Base
scope :life_supporting, where('distance_from_sun > ?', 5).order('diameter ASC')
end
Planet
は、スコープ
life_supporting
と
SolarSystem
has_many :planets
. 私は、has_many リレーションシップを定義したいと思います。
solar_system
に問い合わせたときに、関連するすべての
planets
は、その
life_supporting
のスコープが自動的に適用されます。基本的に、私は
solar_system.planets == solar_system.planets.life_supporting
.
必要条件
-
私は ではない 変更したい
scope :life_supporting
でPlanet
へdefault_scope where('distance_from_sun > ?', 5).order('diameter ASC')
-
に追加する必要がないため、重複を防ぐこともできますね。
SolarSystem
has_many :planets, :conditions => ['distance_from_sun > ?', 5], :order => 'diameter ASC'
目標
のようなものが欲しいです。
has_many :planets, :with_scope => :life_supporting
編集:回避策
phoetが言ったように、ActiveRecordを使ってデフォルトのスコープを実現するのは不可能かもしれません。しかし、私は2つの回避策の可能性を見つけました。どちらも重複を防ぎます。最初のものは、長いですが、明らかな可読性と透明性を維持し、2番目のものは、出力が明示されているヘルパータイプのメソッドです。
class SolarSystem < ActiveRecord::Base
has_many :planets, :conditions => Planet.life_supporting.where_values,
:order => Planet.life_supporting.order_values
end
class Planet < ActiveRecord::Base
scope :life_supporting, where('distance_from_sun > ?', 5).order('diameter ASC')
end
もう一つの解決策は、よりクリーンな方法として、以下のメソッドを単に
SolarSystem
def life_supporting_planets
planets.life_supporting
end
を使用し
solar_system.life_supporting_planets
を使用する場合は
solar_system.planets
.
どちらも質問の答えになっていないので、誰かがこの状況に遭遇したときの回避策として、ここに載せておきます。
どのように解決するのですか?
Rails4では
Associations
には、オプションで
scope
パラメータにラムダを指定し、それを
Relation
に適用されるラムダを受け取ります (cf. the doc for
のドキュメントを参照してください。
)
class SolarSystem < ActiveRecord::Base
has_many :planets, -> { life_supporting }
end
class Planet < ActiveRecord::Base
scope :life_supporting, -> { where('distance_from_sun > ?', 5).order('diameter ASC') }
end
Rails 3では
where_values
を使うことで、回避策が改善されることがあります。
where_values_hash
を使うことで、より良いスコープを扱えるようになります。
where
やハッシュで定義された条件をよりうまく扱うことができるようになります(今回のケースではありません)。
has_many :planets, conditions: Planet.life_supporting.where_values_hash
関連
-
[解決済み] Railsマイグレーションを利用してカラムをドロップする方法
-
[解決済み] SocketError (getaddrinfo: Name or service not known) - Sunspot/Solr Rails development
-
[解決済み] Ruby on Railsのデータベースをパージまたは再作成する
-
[解決済み] Ruby on Railsのマイグレーションでデータベースのカラムの名前を変更するにはどうすればよいですか?
-
[解決済み】Railsのhas_manyがエイリアス名で表示される。
-
[解決済み】Railsのhas_one/has_manyの:sourceオプションについて理解する。
-
[解決済み] githubからあるgemの特定の「コミット」を取得するには?
-
[解決済み] 既存のRailsカラムのbooleanに:default => trueを追加する。
-
[解決済み] Railsで "has_many :through "リレーションはいつ使うのか?
-
[解決済み] カピバラさん曖昧さ解消
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] SocketError (getaddrinfo: Name or service not known) - Sunspot/Solr Rails development
-
[解決済み】rmagick gem install "Can't find Magick-config"...
-
[解決済み】Railsのhas_one/has_manyの:sourceオプションについて理解する。
-
[解決済み] EmacsのRubyオートコンプリートがほぼ使えるようになった
-
[解決済み] Rails 3.1。エンジン vs. マウント可能なアプリ
-
[解決済み] rails3プロジェクトからgemsをアンインストールする最良の方法は何ですか?
-
[解決済み] Herokuで2つのアプリの間でデータベースを共有する
-
[解決済み] Postgres エラー "パラメータ "TimeZone" に無効な値があります。"UTC"
-
[解決済み] Ruby on Rails 3でモジュールを作成し、使用するには?
-
[解決済み] bundlerのダウングレードやrailsのアップグレードはどのように行うのですか?