Skip to content


Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

ActiveRecord::Relation#pluck method

  • Loading branch information...
commit a382d60f6abc94b6a965525872f858e48abc00de 1 parent d9c2882
Bogdan Gusiev bogdan authored
9 activerecord/
@@ -1,5 +1,14 @@
## Rails 3.2.0 (unreleased) ##
+* Implemented ActiveRecord::Relation#pluck method
+ Method returns Array of column value from table under ActiveRecord model
+ Client.pluck(:id)
+ *Bogdan Gusiev*
* Automatic closure of connections in threads is deprecated. For example
the following code is deprecated:
2  activerecord/lib/active_record/associations/collection_proxy.rb
@@ -39,7 +39,7 @@ class CollectionProxy # :nodoc:
instance_methods.each { |m| undef_method m unless m.to_s =~ /^(?:nil\?|send|object_id|to_a)$|^__|^respond_to|proxy_/ }
delegate :group, :order, :limit, :joins, :where, :preload, :eager_load, :includes, :from,
- :lock, :readonly, :having, :to => :scoped
+ :lock, :readonly, :having, :pluck, :to => :scoped
delegate :target, :load_target, :loaded?, :scoped,
:to => :@association
2  activerecord/lib/active_record/base.rb
@@ -449,7 +449,7 @@ class << self # Class methods
delegate :select, :group, :order, :except, :reorder, :limit, :offset, :joins,
:where, :preload, :eager_load, :includes, :from, :lock, :readonly,
:having, :create_with, :uniq, :to => :scoped
- delegate :count, :average, :minimum, :maximum, :sum, :calculate, :to => :scoped
+ delegate :count, :average, :minimum, :maximum, :sum, :calculate, :pluck, :to => :scoped
def inherited(child_class) #:nodoc:
# force attribute methods to be higher in inheritance hierarchy than other generated methods
17 activerecord/lib/active_record/relation/calculations.rb
@@ -166,6 +166,23 @@ def calculate(operation, column_name, options = {})
+ # This method is designed to perform select by a single column as direct SQL query
+ # Returns <tt>Array</tt> with values of the specified column name
+ # The values has same data type as column.
+ #
+ # Examples:
+ #
+ # Person.pluck(:id) # SELECT FROM people
+ # Person.uniq.pluck(:role) # SELECT DISTINCT role FROM people
+ # Person.where(:confirmed => true).limit(5).pluck(:id)
+ #
+ def pluck(column_name)
+ scope =
+ self.connection.select_values(scope.to_sql).map! do |value|
+ type_cast_using_column(value, column_for(column_name))
+ end
+ end
def perform_calculation(operation, column_name, options = {})
25 activerecord/test/cases/calculations_test.rb
@@ -1,5 +1,6 @@
require "cases/helper"
require 'models/company'
+require "models/contract"
require 'models/topic'
require 'models/edge'
require 'models/club'
@@ -446,4 +447,28 @@ def test_distinct_is_honored_when_used_with_count_operation_after_group
distinct_authors_for_approved_count =, :distinct => true)[true]
assert_equal distinct_authors_for_approved_count, 2
+ def test_pluck
+ assert_equal [1,2,3,4], Topic.order(:id).pluck(:id)
+ end
+ def test_pluck_type_cast
+ topic = topics(:first)
+ relation = Topic.where(:id =>
+ assert_equal [ topic.approved ], relation.pluck(:approved)
+ assert_equal [ topic.last_read ], relation.pluck(:last_read)
+ assert_equal [ topic.written_on ], relation.pluck(:written_on)
+ end
+ def test_pluck_and_uniq
+ assert_equal [50, 53, 55, 60], Account.order(:credit_limit).uniq.pluck(:credit_limit)
+ end
+ def test_pluck_in_relation
+ company = Company.first
+ contract = company.contracts.create!
+ assert_equal [], company.contracts.pluck(:id)
+ end
9 railties/guides/source/active_record_querying.textile
@@ -1146,6 +1146,15 @@ h3. +select_all+
Client.connection.select_all("SELECT * FROM clients WHERE id = '1'")
+h3. +pluck+
+<tt>pluck</tt> can be used to query single column from table under model. It accepts column name as argument and returns Array of values of the specified column with corresponding data type.
+Client.where(:active => true).pluck(:id) # SELECT id FROM clients WHERE
+Client.uniq.pluck(:role) # SELECT DISTINCT role FROM clients
h3. Existence of Objects
If you simply want to check for the existence of the object there's a method called +exists?+. This method will query the database using the same query as +find+, but instead of returning an object or collection of objects it will return either +true+ or +false+.

46 comments on commit a382d60


+1 This looks super useful!

Adam Hawkins

+1 agree

Kennon Ballou

As someone who has literally had to write ""id").collect(&:id)" four times today, this is a big +1 from me!

Bryce Thornton

I've wanted a method like this for so long! I'm always writing little bits of code to do this. Thanks!

Philippe Creux

+1 !

Gimi Liang

Agree with @kennon, no'col').map(&:col) any more!

Christopher Jones

+1 Very useful!

Collin Shepherd

Can't try this out at the the moment, so here's a question: How would this compare to ? Same thing / functionality?

Ben Scheirman

pluck yeah ;)

Paweł Gościcki

+1 really useful piece of code

Andrew Kalek

+1 ;)

Guilherme da Silva Mello

Why not several columns? Wouldn't it be as useful? or am I missing something here?

Marty Zalega

+2 because it's that good

Pierre Nespo

Thanks a lot!

Dmitriy Kiriyenko

Does it work with serialization like ernie/valium?

Collin Shepherd

@dmitriy-kiriyenko Since no one answered my previous question about how it compares to valium, and judging by the other comments, I'd say no one here actually knew about valium.

Gimi Liang

@cvshepherd just got to know valium, and I think it's better.


is "pluck" really the right name for this ?

Alexandre de Oliveira

+1: Is "pluck" really the right name for this ?

Matt White

Seriously, I would propose 'project' as a better name


'project' is just as un-obvious. For a method that returns an array of columns I'd expect the method name to have something to do with getting an array of columns....

Something like 'selective_columns' and extend it to return optionally more than one column.

Matt White

It's not un-obvious if you've heard of an SQL projection

Dmitriy Kiriyenko

values_at? =)

Dmitriy Kiriyenko

But I definitely like project. +1 for project.
We'll have another reserved word to avoid in business code.

Alexandre de Oliveira

+1, but I doubt it'll be changed anyway.

Cameron Knight

Being able to "pluck" multiple columns would be quite useful as well.

Mario Visic

+1 although I think values_at (what valium uses) would be a better name than pluck.

Colin MacKenzie IV

+1, but I actually like "pluck". It's used pretty rarely in everyday speech, and to me seeing it is odd enough that I'll remember it as a method name. -- like "tap", the other most awesome method name ever! Plus, "pluck" is such a fun word!


:+1: , I actually think values_at is better than pluck or project

Ali Anwar

+1 multiple columns

Marcel Morgan

+1 multiple columns

Jeremy Kemper

bike shed

Matt White

Green??? What a stupid color for a bikeshed.

But seriously, project is a better name ;)

Dmitriy Kiriyenko

@whitethunder, I told them, but they don't trust me. Seriously, project is an excellent name. More, I'm looking forward for a method like "user" or "company". Also a great idea would be methods "topic", "post" and "comment". =)

Ernie Miller

For those who were asking, it looks like this patch handles serialized columns, because Column#type_cast decodes encoded columns in current master.

This wasn't the case in 3-0-stable, which is why Valium's implementation is (only slightly) more involved.

I agree with @jeremy, though -- this is a whole lot of discussion for a very simple change. In fact, I'd have submitted Valium's implementation as a patch long ago if I'd thought it had a chance to be accepted. One of those things where it was so ridiculously simple that I figured there was a reason it wasn't part of the AR API already. ;)

Ernie Miller

Hmm. I take back my comment about working with serialization. It looks like the only place that a Column's coder is being set in the current AR code is in 3 tests in column_definition_test at this point, unless I missed something. It doesn't look like SchemaCache would be the right place to handle this, either.

Anyway, I have a rough version of Valium's take on this ported to a Rails 3.2 patch and passing all but the serialization tests (due to the issue mentioned). I can work out the remaining issues there and submit a value(s)_of implementation for Rails 3.2 if the core team is interested.

Jeremy Kemper

@ernie Cool, yeah, let's see it. Wish we'd known you had Valium already implemented, sorry about that. Pull request came in; didn't look for prior art. Thanks for pitching in in any case.

Ernie Miller

@jeremy pushing it up now -- thanks!

Ernie Miller

For those visiting this thread: See #3871 for the pull request with alternate implementation supporting serialization, multiple values, etc.

Aaron Patterson


Ernie Miller

@tenderlove unicorns, rainbows and ponies would be the "etc" part

Cristiano Betta

Love it! +1

Fabricio Quagliariello

wow, amazing +1

Please sign in to comment.
Something went wrong with that request. Please try again.