2015-12-28 6 views
2

У меня есть следующие классы:Rails Mysql: Как включить только объект отношения has_many, который соответствует моему состоянию?

class User < ActiveRecord::Base 
     has_many :keys 
    end 

    class Key < ActiveRecord::Base 
     belongs_to :room 
    end 

    class Room < ActiveRecord::Base 
     #has column "surface_area" 
    end 

Я хочу, чтобы запросить все пользователи, имеющие ключи с номерами с surface_area 10, только в том числе ключи с номерами, которые имеют площадь поверхности 10.

I имеют следующий запрос:

User.joins(keys: :room).where('room.surface_area= ?', 10) 

Это возвращает пользователей, которые имеют ключи с room.surface_area 10, но она включает в себя все ключи, так и ключи, которые имеют номер с различной площадью поверхности, чем 10. Я только хочу вернуть подсайты и др ключей, которые имеют номер с площадью поверхности 10.

Wrong возвращаемого значения:

Users:{ 
keys: [ 
    {id: 1, surface_area: 11}, 
    {id: 2, surface_area: 10}, 
    {id: 3, surface_area: 10} 
] 
} 

Правильное значение возврата:

Users:{ 
    keys: [ 
     {id: 2, surface_area: 10}, 
     {id: 3, surface_area: 10} 
    ] 
    } 

json.rabl файл для пользователей

collection @users, :root => :users, :object_root => false 

child :keys do 
    extends "keys" 
end 
+0

'User.joins (keys:: room) .where (room: {surface_area: 10})' try this –

ответ

1
User.joins(keys: :room).where('room.surface_area= ?', 10) 

Этот co mmand запрашивает пользователей и возвращает пользователей, имеющих ключи для комнат с площадью поверхности 10. Это правильно. Но когда вы вызываете keys на одного из этих пользователей, вы получаете все ключи, которые у них есть. И это тоже правильно, потому что это то, что делает has_many :keys.

Что вам нужно, чтобы определить новый метод экземпляра в модели пользователя, например, так:

def keys_for_rooms_with_surface_area(area) 
    keys.joins(:room).where('rooms.surface_area = ?', area) 
end 

Если вы хотите has_many :keys всегда возвращать ключи для помещений с площадью поверхности = 10, вы можете сделать это так :

has_many :keys, ->() { joins(:room).where('rooms.surface_area = 10') } 

В этом случае ваш самый первый запрос будет выглядеть следующим образом:

User.joins(keys: :room) 
+1

Да, я просто добавил метод 'keys_for_rooms_with_surface_area (area)' в User и вызвал функцию из .rabl-файла, и это работает спасибо! – MeesterPatat

0

Почему бы не попробовать ...

#app/models/user.rb 
class User < ActiveRecord::Base 
    has_many :keys do 
     def surface_area surface_area 
     joins(:room).where(room: { surface_area: surface_area }) 
     end 
    end 
end 

Это должно дать вам возможность вызова:

@user = User.find params[:id] 
@user.keys.surface_area 10 

Я удалю, если она не работает, просто удар в темноте