Rails / Arel: выбор всех записей как ActiveRecord :: Relation - PullRequest
31 голосов
/ 08 апреля 2011

Использование Arel в Rails - я ищу способ создания ActiveRecord::Relation, который эффективно приводит к SELECT * FROM table, которым я все еще могу манипулировать.

Например, у меня есть модель, котораяразделить на несколько категорий, и я возвращаю счетчики для них следующим образом:

relation = Model.where(:archived => false) # all non-archived records
record_counts = {
  :total => relation.count,
  :for_sale => relation.where(:for_sale => true).count
  :on_auction => relation.where(:on_auction => true).count
}

Это прекрасно работает и имеет преимущество в том, что запускает COUNT запросов к MySQL, а не фактически выбирает записисами по себе.

Однако теперь мне нужно включить в счет архивные записи, но relation = Model.all приводит к Array, и я ищу ActiveRecord::Relation.

.Единственный способ, которым я могу думать об этом, это model.where(model.arel_table[:id].not_eq(nil)), который работает, но кажется немного абсурдным.

Может ли кто-нибудь пролить свет на это?

Ответы [ 3 ]

48 голосов
/ 08 апреля 2011

Попробуйте relation = Model.scoped. Это даст вам отношение вместо фактических результатов.

11 голосов
/ 30 января 2015

Для Rails 4.1 и выше: Model.all возвращает отношение (где оно ранее не было)

Для Rails 4.0: Model.where(nil)

Для Rails 3.x: Model.scoped

1 голос
/ 08 апреля 2011

Вы бы хотели:

relation = Model.scoped

, который, если вы видите, что такое отношение, на самом деле это ActiveRecord::Relation.

Как вы можете видеть на этой странице:

http://api.rubyonrails.org/classes/ActiveRecord/NamedScope/ClassMethods.html#method-i-scoped

В нем говорится следующее:

Анонимные области, как правило, полезны при процедурной генерации сложных запросов, когда промежуточные значения (области) передаются как первый классобъекты это удобно.

...