如何将SQL查询转换为Rails Active Record Query?

时间:2011-08-10 19:14:36

标签: mysql sql ruby-on-rails-3 postgresql scope

我的上一篇文章是关于在LEFT OUTER JOIN上编写带有条件的SQL查询的最佳方法:
LEFT OUTER JOIN with conditions (where, order by)?

现在,我需要将这个优秀的SQL转换为甜蜜的Active Record Query(Rails 3)。 ; - )

我有2个型号:

培训 has_many:training_histories

TrainingHistory belongs_to:training

如何编写范围以获取下面的SQL检索结果?

SELECT tc.id, tc.name, tc.order, 
th.id as history_id, th.finished_at, th.score
FROM trainings tc
LEFT OUTER JOIN training_histories th ON th.training_id = tc.id 
    and th.id =
    (SELECT th1.id from training_histories th1 where th1.training_id = tc.id
     and th1.finished_at is not null
     order by th1.finished_at desc limit 1)
WHERE tc.id > 4
AND tc.id < 8
GROUP BY tc.id
ORDER BY tc.order_by ASC, tc.id ASC

我想检索TRAININGS的所有记录,并添加TRAINING_HISTORIES的最后一个有效(又名完成)相关记录。

有什么建议吗?

谢谢

1 个答案:

答案 0 :(得分:7)

对于rails 3,试试这个:

Training.select("trainings.id, trainings.name, trainings.order, 
                 trainings.id AS history_id, training_histories.finished_at,
                 training_histories.score").
         joins("LEFT OUTER JOIN training_histories 
                ON training_histories.training_id = trainings.id 
                AND training_histories.id = (SELECT th1.id FROM training_histories th1          
                                             WHERE th1.training_id = tc.id
                                             AND th1.finished_at IS NOT NULL
                                             ORDER BY th1.finished_at DESC LIMIT 1)").
         where("trainings.id > 4 AND trainings.id < 8").
         group("trainings.id").
         order("trainings.order_by ASC, trainings.id ASC")

基本上,您只是将预先编写的查询转换为Rails 3 finder方法。