May 1, 2017
This blog is part of our Rails 5.1 series.
Let's say that we want to know all the deliveries in progress for an order.
The following code would do the job.
class Order
has_many :deliveries
def num_deliveries_in_progress
deliveries.select { |delivery| delivery.in_progress? }.size
end
end
But usage of count
should make more sense over a select
, right?
class Order
has_many :deliveries
def num_deliveries_in_progress
deliveries.count { |delivery| delivery.in_progress? }
end
end
However the changed code would return count for all the order deliveries, rather than returning only the ones in progress.
That's because ActiveRecord::Relation#count
silently discards the block
argument.
Rails 5.1 fixed this issue.
module ActiveRecord
module Calculations
def count(column_name = nil)
if block_given?
to_a.count { |*block_args| yield(*block_args) }
else
calculate(:count, column_name)
end
end
end
end
So now, we can pass a block to count
method.
If this blog was helpful, check out our full blog archive.