Rails 7.1 allows ActiveRecord reselect to accept a hash
Rails 7.1 allowed ActiveRecord::QueryMethods#select
to receive hash values.
The reselect
method needed this functionality added.
Within the same Rails 7.1 release,
the Rails team adds the ability to pass a hash
to the ActiveRecord#reselect
method.
Before Rails 7.1
ActiveRecord#reselect method
The reselect
method in ActiveRecord is a powerful tool for fine-tuning
the columns retrieved from your database queries.
Think of it as adding a layer of precision to your existing query,
allowing you to focus on the specific data you need.
reselect
accepts various arguments,
with the most common being:
-
Symbols: Specify the columns you want to select.
-
Strings: Provide raw SQL expressions for custom selection.
# select 'id' and 'name' from 'users' table
users = User.all.reselect(:id, :name)
# select 'created_at' with alias 'date_joined'
users = users.reselect(created_at: :date_joined)
# remove 'email' from the selection
users = users.reselect(:id, :name).except(:email)
As seen in the above example,
you can update what columns are retrieved after choosing
specific ones with ActiveRecord's reselect
.
When working with joins, you need to pass raw SQL strings as shown below:
posts = Post
.joins(:author)
.select('posts.title', 'authors.name')
posts = posts
.reselect(
'posts.title',
'authors.name',
)
# Now posts will have all three columns for each record
If you try to pass a hash to the reselect
method,
it fails to execute
and
raises an Unsupported argument type: Hash
error.
posts = posts
.reselect(
:title,
authors: [:name]
)
An error occurred when inspecting the object: #<Arel::Visitors::UnsupportedVisitError: Unsupported argument type: Hash. Construct an Arel node instead.>
...
In Rails 7.1
Rails 7.1 allows the ActiveRecord reselect method to accept the
hash of columns and aliases.
Passing the hash to the reselect
method executes
the query successfully without raising any error.
The benefits of using a hash in the reselect
method are:
-
Enhanced Readability: Your code becomes cleaner and more expressive, revealing the exact data you target for the primary model and its associations.
-
Greater Flexibility: Easily adjust the selected columns and aliases for the primary model and its associations without rewriting the entire query.
Here's how you can define selections for associations:
Symbol Shortcuts
For more straightforward associations, you can automatically use specific symbols to include commonly desired columns for the associated model.
posts = Post.all.reselect(
id: :post_id,
title: :post_title,
authors: [:name]
)
Nested Hashes
Use nested hashes to represent each associated model and its desired columns.
posts = Post.all.reselect(
id: :post_id,
title: :post_title,
authors: {
name: :author_name,
}
)
To know more about this feature, please refer to this PR.