Method: ActiveRecord::QueryMethods#select

Defined in:
lib/active_record/relation/query_methods.rb

#select(*fields) ⇒ Object

Works in two unique ways.

First: takes a block so it can be used just like Array#select.

Model.all.select { |m| m.field == value }

This will build an array of objects from the database for the scope, converting them into an array and iterating through them using Array#select.

Second: Modifies the SELECT statement for the query so that only certain fields are retrieved:

Model.select(:field)
# => [#<Model id: nil, field: "value">]

Although in the above example it looks as though this method returns an array, it actually returns a relation object and can have other query methods appended to it, such as the other methods in ActiveRecord::QueryMethods.

The argument to the method can also be an array of fields.

Model.select(:field, :other_field, :and_one_more)
# => [#<Model id: nil, field: "value", other_field: "value", and_one_more: "value">]

The argument also can be a hash of fields and aliases.

Model.select(models: { field: :alias, other_field: :other_alias })
# => [#<Model id: nil, alias: "value", other_alias: "value">]

Model.select(models: [:field, :other_field])
# => [#<Model id: nil, field: "value", other_field: "value">]

You can also use one or more strings, which will be used unchanged as SELECT fields.

Model.select('field AS field_one', 'other_field AS field_two')
# => [#<Model id: nil, field_one: "value", field_two: "value">]

If an alias was specified, it will be accessible from the resulting objects:

Model.select('field AS field_one').first.field_one
# => "value"

Accessing attributes of an object that do not have fields retrieved by a select except id will throw ActiveModel::MissingAttributeError:

Model.select(:field).first.other_field
# => ActiveModel::MissingAttributeError: missing attribute 'other_field' for Model


390
391
392
393
394
395
396
397
398
399
400
401
402
403
# File 'lib/active_record/relation/query_methods.rb', line 390

def select(*fields)
  if block_given?
    if fields.any?
      raise ArgumentError, "`select' with block doesn't take arguments."
    end

    return super()
  end

  check_if_method_has_arguments!(__callee__, fields, "Call `select' with at least one field.")

  fields = process_select_args(fields)
  spawn._select!(*fields)
end