counter_cache has_many_through sql optimisation, reduce number of sql queries

萝らか妹 提交于 2019-12-30 01:36:11

问题


How I can optimise my SQL queries, to ignore situations like this:

Meeting.find(5).users.size => SELECT COUNT(*) FROM ... WHERE ...

User.find(123).meetings.size => SELECT COUNT(*) FROm ... WHERE ...

I have no idea how to use counter_cache here.

Here is my model relation:

class Meeting < ActiveRecord::Base
  has_many :meeting_users
  has_many :users, :through => meeting_users
end

class User < ActiveRecord::Base
  has_many :meeting_users
  has_many :meetings, :through => meeting_users
end

class Meeting_user < ActiveRecord::Base
  belongs_to :meeting
  belongs_to :user
end

What are the most optimal solutions ?

And how implement counter_cache here ?


回答1:


As far as I know you can't use counter_cache with through associations, that's why you should manually increment it.

For example (untested):

class MeetingUser < ActiveRecord::Base

  ...

  after_create { |record| 
    Meeting.increment_counter(:users_count, record.meeting.id)
  }

  after_destroy { |record| 
    Meeting.decrement_counter(:users_count, record.meeting.id)
  }

end



回答2:


Starting from Rails3.0.5 and in newer versions, you are now able to set counter cache to the "linker" model, in your case it will be:

class MeetingUser < ActiveRecord::Base
  belongs_to :meeting, :counter_cache => :users_count
  belongs_to :user, :counter_cache => :meetings_count
end

It's important to explicitly specify count column names, otherwise the columns used will default to meeting_users_count.



来源:https://stackoverflow.com/questions/4700247/counter-cache-has-many-through-sql-optimisation-reduce-number-of-sql-queries

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!