简体   繁体   中英

Create a scope in rails based on HABTM association count

I'm trying to create a rails scope based on the count of a model's HABTM assocation, but I'm struggling with the SQL.

I want Match.open to return matches with less than two users. I also have Match.upcoming, which returns matches with a 'future_date' in the future, which is working well.

My code:

class Match < ActiveRecord::Base
  has_and_belongs_to_many :users

  scope :open, joins('matches_users').
      select('*').
      group('matches.id').
      having('count(matches_users.user_id) < 2')


scope :upcoming, lambda {
    where("proposed_date between ? and ?", Date.today, Date.today.next_month.beginning_of_month)
}

I'm currently getting the error:

SQLite3::SQLException: no such column: matches_users.user_id: SELECT * FROM "matches" matches_users GROUP BY matches.id HAVING count(matches_users.user_id) < 2

ActiveRecord::StatementInvalid: SQLite3::SQLException: no such column: matches_users.user_id: SELECT * FROM "matches" matches_users GROUP BY matches.id HAVING count(matches_users.user_id) < 2

I'm currently achieving this with a class method:

def self.open
    self.select{|match| match.users.length < 2}
end

Which works, but I'd really like to move this into a scope for speed, and so that I can chain the scopes like Match.open.upcoming.

What am I doing wrong here? What's the correct way to do this? Any help would be appreciated.

Give this a shot - I've used something similar before and it seems to work for me:

class Match < ActiveRecord::Base
  has_and_belongs_to_many :users

  scope :open, joins(:matches_users)
               .select('matches.*')
               .group('matches.id')
               .having('count(matches_users.id) < 2')

...

end

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM