简体   繁体   中英

why is Model.all different to Model.where('true') in rails 3

I have a query, which works fine:

ModelName.where('true')

I can chain this with other AR calls such as where, order etc. However when I use:

ModelName.all

I receive the "same" response but can't chain a where or order to it as it's an array rather than a AR collection. Whereas I have no pragmatic problem using the first method it seems a bit ugly/unnecessary. Is there a cleaner way of doing this maybe a.to_active_record_collection or something?

There is an easy solution. Instead of using

ModelName.where('true')

Use:

ModelName.scoped

As you said:

ModelName.where('true').class #=> ActiveRecord::Relation

ModelName.all.class #=> Array

So you can make as many lazy loading as long as you don't use all , first or last which trigger the query.

It's important to catch these differences when you consider caching.

Still I can't understand what kind of situation could lead you to something like:

ModelName.all.where(foobar)

... Unless you need the whole bunch of assets for one purpose and get it loaded from the database and need a subset of it to other purposes. For this kind of situation, you'd need to use ruby's Array filtering methods.


Sidenote:

 ModelName.all

should never be used, it's an anti-pattern since you don' control how many items you'll retrieve. And hopefully:

 ModelName.limit(20).class #=> ActiveRecord::Relation

As you said, the latter returns an array of elements, while the former is an ActiveRecord::Relation . You can order and filter array using Ruby methods. For example, to sort by id you can call sort_by(&:id) . To filter elements you can call select or reject . For ActiveRecord::Relation you can chain where or order to it, as you said.

The difference is where the sorting and processing goes. For Array, it is done by the application; for Relation - by the database. The latter is usually faster, when there is more records. It is also more memory efficient.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM