2014-11-21 1 views
0

Я пытаюсь получить сумму days_to_complete для всех training_stages, у которых есть хотя бы один training_tasks с is_complete: => false. (Обратите внимание, что я работаю в двигатель под названием Training)ActiveRecord SUM отдельных записей, которые имеют ребенка, соответствующего условию

create_table :training_stages do |t| 
    t.references :checklist, index: true 
    t.string :name 
    t.integer :days_to_complete 

    t.timestamps 
end 

create_table :training_tasks do |t| 
    t.references :stage, index: true 
    t.string :description 
    t.boolean :is_public, default: false, null: false 
    t.boolean :is_complete, default: false, null: false 

    t.timestamps 
end 

Пример данных

training_stages: 
    id checklist_id name days_to_complete created_at updated_at 
    1 1 Intake Stage 8 2014-11-21 21:03:53 2014-11-21 21:03:53 
    2 1 Document State 6 2014-11-21 21:03:53 2014-11-21 21:03:53 

training_tasks: 
    id stage_id description is_public is_complete created_at updated_at 
    1 1 Task1 1 0 2014-11-21 21:03:53 2014-11-21 21:03:53 
    2 1 Task2 0 0 2014-11-21 21:03:53 2014-11-21 21:03:53 
    3 1 Task3 1 0 2014-11-21 21:03:53 2014-11-21 21:03:53 
    4 2 Task4 1 0 2014-11-21 21:03:53 2014-11-21 21:03:53 
    5 2 Task5 0 0 2014-11-21 21:03:53 2014-11-21 21:03:53 
    6 2 Task6 1 0 2014-11-21 21:03:53 2014-11-21 21:03:53 
    7 2 Task7 0 0 2014-11-21 21:03:53 2014-11-21 21:03:53 

Когда я запускаю следующее, я получаю 48.

# Assume that stages already contains Stage.all 
stages.includes(:tasks) 
    .where(training_tasks: {is_complete: false}) 
    .sum(:days_to_complete) 

Похоже, что это возвращает этап для каждой задачи, которая соответствует условию, а затем суммирует их все. Затем я попытался группировки:

stages.includes(:tasks) 
    .where(training_tasks: {is_complete: false}) 
    .group("training_stages.id") 
    .sum(:days_to_complete) 

Это фактически возвращает {1=>24, 2=>24}

Как я могу ограничить сумму только отдельные этапы?

ответ

0

В RoR вы можете сделать

stages.includes(:tasks) 
.where(training_tasks: {is_complete:false}) 
.distinct.pluck(:days_to_complete).sum 

или

stages.includes(:tasks) 
.where(training_tasks: {is_complete:false}) 
.distinct.to_a.sum(&:days_to_complete) 
Смежные вопросы