2015-02-08 95 views
0

说我有3个表我可以在我使用ActiveRecord的表上指定一个where查询吗?

  1. 医生,
  2. doctor_relationships &
  3. 用户

    • 用户必须通过doctor_relationships许多医生
    • 医生必须通过doctor_relationships很多用户
    • 用户有很多文档tor_relationships
    • 医生有许多doctor_relationships
    • doctor_relationship属于医生
    • doctor_relationship属于一个用户

有在doctor_relationships一列, :visited?一个布尔值

查询所有访问某位医生的用户的最佳方式是什么

我试图

@doctor=doctor.first 
doctor.doctor_relationships.where(visited: true) 

这让我的医生的关系我想,但我不能说对活动的记录关系。用户。唯一的方法就是循环处理活动记录关系中的每个关系,并调用.user,还是有更好的ActiveRecord友好方式? ex。

doctor.doctor_relationships.where(visited: true).each do |relationship| 
    relationship.user 
end 

回答

2

在这类情况下,我觉得有用反转在我的头上的关系。你想要什么东西?从该模型开始,查询变得更容易思考。

这给了我们:

User.joins(doctor_relationships: :doctor).where(doctor_relationships: {visited: true, doctor: @doctor}) 

虽然这将让你你在寻找什么,它的丑陋。让我们改进它!

现在我假设你的类是这样的:

class User < ActiveRecord::Base 
    has_many :doctor_relationships 
    has_many :doctors, through: :doctor_relationships 
end 

class DoctorRelationship < ActiveRecord::Base 
    belongs_to :user 
    belongs_to :doctor 
end 

class Doctor < ActiveRecord::Base 
    has_many :doctor_relationships 
    has_many :users, through: :doctor_relationships 
end 

我觉得这是一个要好很多,如果你能对这种情况下的东西,如查询:

doctor.visits 
doctor.patients 

要做到这一点,你需要修改模型如下:

class Doctor < ActiveRecord::Base 
    has_many :doctor_relationships 
    has_many :visits, -> { where(visited: true) }, class_name: 'DoctorRelationship' 
    has_many :patients, through: :visits, source: :user 
    has_many :users, through: :doctor_relationships 
end 

我们在这里做的是告诉活动记录,我们是这样一个联合体,visits,当visitedtrueDoctorRelationship,只有存在。然后,我们使用该关联来定义另一个关联,patients,它只会返回实际访问过医生的那些用户。

这种方法(除了可读的代码)的好处是,它也产生高效的查询:

SELECT "users".* FROM "users" INNER JOIN "doctor_relationships" ON "users"."id" = "doctor_relationships"."user_id" WHERE "doctor_relationships"."doctor_id" = ? AND "doctor_relationships"."visited" = 't' 

这恰好是完全相同的查询,在开始了更详细的ActiveRecord的代码给了我们。得分了!

0

好开始从用户模式查询的话,我相信这样的事情应该工作

@doctor = whatever 
User.joins(:doctor_relationships) 
    .where(doctor_relationships: {visited: true, doctor: @doctor}) 
相关问题