2010-01-15 6 views
19

В моей модели post.rb, у меня есть default_scope :conditions => {:deleted => 'false'}Перекрытие default_scope в Rails

Но если я пытаюсь запустить Post.find(:all, :conditions => "deleted='false'"), это ничего не вернется. Это как если бы default_scope имел приоритет над всем.

Я хочу, чтобы в случае, когда я делаю Post.find(), он не возвращает удаленные сообщения, но я также хотел бы иметь доступ к ним, если нужно. Что нужно изменить в моем запросе или моей модели Rails?

Спасибо.

+0

'default_scope' * * имеет приоритет над всем. Я написал ответ с использованием 'named_scope' в ваш предыдущий вопрос, который, я думаю, применим и здесь: http://stackoverflow.com/questions/2073197/how-to-get-a-model-to-specify-a- pre-requisit-condition/2073858 # 2073858 – jerhinesmith

ответ

17

with_exclusive_scope является protected, так что вы должны создать метод класса:

def self.include_deleted_in 
    Event.with_exclusive_scope { yield } 
end 

то в вызове контроллера

Post.include_deleted_in { Post.find(:all) } 
+0

+1; Спасибо - лучший ответ, который я нашел в сети – Makibo

+0

Event.with_exclusive_scope {yield} не сработал для меня, мне пришлось поставить Post.with_exclusive_scope {yield}. В любом случае отличный ответ. Спаси мою жизнь сегодня. – workdreamer

1

использование with_exclusive_scope

Post.with_exclusive_scope { Post.find(:all) } 
+0

Использование этой модели (вне модели Post) приводит к: защищенный метод 'with_exclusive_scope ', вызываемый для # <класс: 0x10faf5c70> – intepid

+0

Вы можете использовать' Post.send (: with_exclusive_scope) {.. .} ' –

1

Прицелы предназначены для компонуемы, то есть вы можете объединить кучу из них, и он эффективно применяет все условия. В этом случае ActiveRecord слишком наивна, чтобы определить, что явное условие должно отрицать первое. Он просто строит запрос, объединяющий все предложения с помощью AND. По этой причине default_scope имеет наибольшую полезность с предложениями: order, которые не являются составными (в любом случае в реализации ActiveRecord 2.3). Больше обсуждений here.

Также обратите внимание, что в Rails 3 ActiveRecord используется Arel для большого количества запросов, что значительно увеличит мощность генерации запросов ActiveRecord и упростит многие внутренние функции. Вполне вероятно, что с Arel улучшит вашу ситуацию. Тем временем я рекомендую не устанавливать условия в default_scope, если нет строк, которые вы действительно хотите быть невидимыми для своего приложения Rails.

60

Это один был как-то левый скрытый :)

Просто используйте Post.unscoped.where(:deleted => true), если вы используете Rails 3

Кредит составляет José Valim.

+0

Кажется, что не работает, когда default_scope имеет предложение: order и вы хотите его переопределить. – Zabba

+2

Забба, это было точно мое дело, и это безупречно работало для меня. спасибо edgerunner. – taelor

+0

@ Zabba, используйте 'reorder' для этого – edgerunner

Смежные вопросы