情報セキュリティの制約により、製品にはデフォルトのスコープがあります。
_class Product < ActiveRecord::Base
has_many :photos
default_scope where('visible = 1')
end
_
ただし、関連付けられている写真モデルでは、表示されるべきではない製品も見つける必要があります。
_class Photo < ActiveRecord::Base
belongs_to :product
end
my_photo.product
_
他の場合、default_scopeをバイパスするために nscoped を使用できます。 Product.unscoped.find_by_title('abc')
で。しかしながら:
レコードの関連付けを使用するときにスコープを削除する方法は?
_my_photo.unscoped.product
_は、my_photoにunscoped
というメソッドがないため、意味がありません。 _my_photo.product.unscoped
_はすでにnilである可能性があるため、_my_photo.product
_も意味がありません。
ああ。私は自分をだましました。以下はうまくいかないと思ったが...
Product.unscoped do
my_photo.product
end
バイパスする必要があるdefault_scope
を使用して、モデルでunscopedを呼び出す必要があることに注意してください。
また、継承は尊重されなければなりません。 class InsuranceProduct < Product
とclass FinancialProduct < Product
とProduct
にdefault_scope
がある場合、次の2つの組み合わせはすべて機能します。
InsuranceProduct.unscoped do
my_record.insurance_products
end
FinancialProduct.unscoped do
my_record.financial_products
end
Product.unscoped do
my_record.products
end
ただし、次の機能しませんスコープはProduct
で定義されていますが:
Product.unscoped do
my_record.financial_products
end
私はそれがRuby/Rails。
別のオプションは、ゲッターメソッドをオーバーライドし、スーパースコープを解除することです。
class Photo < ActiveRecord::Base
belongs_to :product
def product
Product.unscoped{ super }
end
end
スコープを解除する必要がある関連モデルが1つあるという同じ状況に遭遇しましたが、他のほとんどの場合はデフォルトのスコープが必要でした。これにより、アソシエーションゲッターを複数の場所で使用している場合に、スコープ外の余分な呼び出しを節約できます。
私はおそらくパーティーに少し遅れていますが、しばらく前に私は同じ状況にいることに気付き、これを簡単に行うための宝石を書きました: nscoped_associations 。
使用法:
belongs_to :user, unscoped: true
へのサポート:
多態的な関連付けもサポートされています。
特定の関連付けのスコープを常に解除する必要がある場合は、関連付けを定義するときにスコープを解除できます。
belongs_to :product, -> { unscope(where: :visible) }
何らかの理由で、特定のwhere
キーが正しく読み込まれなかったため、where
全体のスコープを解除しました。これは、私の場合にうまくいく別のオプションです。
belongs_to :product, -> { unscope(:where) }
他の答えも見る価値がありますが、これはRails 4.1+。
Rails 4では、望ましくないフィルターの明示的なスコープ解除との関連付けを使用できます。つまり、my_photo.product.unscope(where: :visible)
メイントピックではなく、ActiveRecord#becomesの問題についてです。初期化子で(できれば)修正しました。
[。 @association_cache) は end alias_method_chain:becomes、:association_cache end になりました
この質問 は、関連付けのデフォルトのwhere句をバイパスする方法を見つけるのに役立ちます。
ただし、スコープを定期的に回避する必要がある場合は、おそらくデフォルトにする必要があることを繰り返す価値があります。 visible
のデフォルト以外のスコープを作成し、関連付けで明示的に使用します。