Nanego
Nanego

Reputation: 1905

Faster way to find the last updated timestamp

I expect this call

Model.maximum(:updated_at)

to be faster than this one

Model.order(:updated_at).last.updated_at

Is anyone able to confirm this assertion? and, if true, explain why?

Upvotes: 12

Views: 7589

Answers (2)

Mori
Mori

Reputation: 27779

You can use the the Benchmark module to investigate easily, e.g.:

require 'benchmark'

n = 50000
Benchmark.bm do |x|
  x.report('maximum') { n.times.do; v1; end }
  x.report('order-pluck') { n.times do; v2; end }
end

def v1
  clear_cache
  Model.maximum(:updated_at)
end

def v2
  clear_cache
  Model.order(:updated_at).pluck(:updated_at).last
end

def clear_cache
  ActiveRecord::Base.connection.query_cache.clear
end

To make it worth doing this with n > 1 you'll have to clear the various caches that might be involved. There may well be a cache in your db server, separate from the ActiveRecord cache. For instance to clear the Mysql cache you could call:

`mysql mydb -e 'RESET QUERY CACHE'`

Upvotes: 6

Yury Lebedev
Yury Lebedev

Reputation: 4005

Your expectation is correct.

When you call Model.maximum(:updated_at), you ask your DB to return just a single value.

When you call Model.order(:updated_at).pluck(:updated_at).last, your database returns you all the values for the updated_at column in the table, which consumes more memory (because you have to build a big array), and takes more time.

Upvotes: 1

Related Questions