diff --git a/app/controllers/overview_controller.rb b/app/controllers/overview_controller.rb index 1bbf4d4e..b9274f9d 100644 --- a/app/controllers/overview_controller.rb +++ b/app/controllers/overview_controller.rb @@ -15,5 +15,7 @@ class OverviewController < SqmApplicationController @category_presenters = @page.category_presenters @student_response_rate_presenter = @page.student_response_rate_presenter @teacher_response_rate_presenter = @page.teacher_response_rate_presenter + @parent_response_rate_presenter = @page.parent_response_rate_presenter end end + diff --git a/app/presenters/category_presenter.rb b/app/presenters/category_presenter.rb index 4da6749d..5a11f359 100644 --- a/app/presenters/category_presenter.rb +++ b/app/presenters/category_presenter.rb @@ -88,4 +88,3 @@ class CategoryPresenter '5': "heart" } end end - diff --git a/app/presenters/overview/overview_presenter.rb b/app/presenters/overview/overview_presenter.rb index 94fae8b9..6dc489c7 100644 --- a/app/presenters/overview/overview_presenter.rb +++ b/app/presenters/overview/overview_presenter.rb @@ -27,7 +27,7 @@ class Overview::OverviewPresenter "school-quality-frameworks" end - def show_response_rates + def show_student_response_rates view == "student" end @@ -36,11 +36,15 @@ class Overview::OverviewPresenter end def student_response_rate_presenter - ResponseRatePresenter.new(focus: :student, school: @school, academic_year: @academic_year) + StudentResponseRatePresenter.new(school: @school, academic_year: @academic_year) end def teacher_response_rate_presenter - ResponseRatePresenter.new(focus: :teacher, school: @school, academic_year: @academic_year) + TeacherResponseRatePresenter.new(school: @school, academic_year: @academic_year) + end + + def parent_response_rate_presenter + ParentResponseRatePresenter.new(school: @school, academic_year: @academic_year) end def presenter_for_measure(measure) diff --git a/app/presenters/overview/parent_overview_presenter.rb b/app/presenters/overview/parent_overview_presenter.rb index 46dfa898..466c3abf 100644 --- a/app/presenters/overview/parent_overview_presenter.rb +++ b/app/presenters/overview/parent_overview_presenter.rb @@ -30,3 +30,4 @@ class Overview::ParentOverviewPresenter < Overview::OverviewPresenter Overview::VarianceChartRowPresenter.new(construct: scale, score:) end end + diff --git a/app/presenters/overview/variance_chart_row_presenter.rb b/app/presenters/overview/variance_chart_row_presenter.rb index 9147da2c..c9c83ae8 100644 --- a/app/presenters/overview/variance_chart_row_presenter.rb +++ b/app/presenters/overview/variance_chart_row_presenter.rb @@ -114,3 +114,4 @@ class Overview::VarianceChartRowPresenter zones.zone_for_score(@score) end end + diff --git a/app/presenters/parent_response_rate_presenter.rb b/app/presenters/parent_response_rate_presenter.rb new file mode 100644 index 00000000..b221bfe1 --- /dev/null +++ b/app/presenters/parent_response_rate_presenter.rb @@ -0,0 +1,24 @@ +class ParentResponseRatePresenter < ResponseRatePresenter + def initialize(academic_year:, school:) + super(academic_year:, school:) + @survey_items = SurveyItem.parent_survey_items + end + + def actual_count + SurveyItemResponse.includes(:parent).where(school:, academic_year:).where.not(parent_id: nil) + .select(:parent_id) + .distinct + .map { |response| response.parent&.number_of_children } + .compact.sum + end + + def respondents_count + return 0 if respondents.nil? + + respondents.total_students + end + + def focus + "parent" + end +end diff --git a/app/presenters/response_rate_presenter.rb b/app/presenters/response_rate_presenter.rb index 947cce4d..fef8e097 100644 --- a/app/presenters/response_rate_presenter.rb +++ b/app/presenters/response_rate_presenter.rb @@ -1,16 +1,9 @@ class ResponseRatePresenter - attr_reader :focus, :academic_year, :school, :survey_items + attr_reader :academic_year, :school, :survey_items - def initialize(focus:, academic_year:, school:) - @focus = focus + def initialize(academic_year:, school:) @academic_year = academic_year @school = school - if focus == :student - @survey_items = Measure.all.flat_map do |measure| - measure.student_survey_items_with_sufficient_responses(school:, academic_year:) - end - end - @survey_items = SurveyItem.teacher_survey_items if focus == :teacher end def date @@ -40,6 +33,10 @@ class ResponseRatePresenter "Percentages based on #{actual_count} out of #{respondents_count.round} #{focus}s completing at least 25% of the survey." end + def focus + raise "please implment method: focus" + end + private def cap_at_100(value) @@ -47,30 +44,7 @@ class ResponseRatePresenter end def actual_count - if focus == :teacher - response_count_for_survey_items(survey_items:) - else - non_early_ed_items = survey_items - SurveyItem.early_education_survey_items - non_early_ed_count = response_count_for_survey_items(survey_items: non_early_ed_items) - - early_ed_items = survey_items & SurveyItem.early_education_survey_items - early_ed_count = SurveyItemResponse.where(school:, academic_year:, - survey_item: early_ed_items) - .group(:survey_item) - .select(:response_id) - .distinct - .count - .reduce(0) do |largest, row| - count = row[1] - if count > largest - count - else - largest - end - end - - non_early_ed_count + early_ed_count - end + raise "please implement the method: actual_count" end def response_count_for_survey_items(survey_items:) @@ -79,11 +53,7 @@ class ResponseRatePresenter end def respondents_count - return 0 if respondents.nil? - - count = enrollment if focus == :student - count = respondents.total_teachers if focus == :teacher - count + raise "please implement the method: respondents_count" end def enrollment @@ -106,3 +76,4 @@ class ResponseRatePresenter respondents.enrollment_by_grade.keys end end + diff --git a/app/presenters/student_response_rate_presenter.rb b/app/presenters/student_response_rate_presenter.rb new file mode 100644 index 00000000..530528c6 --- /dev/null +++ b/app/presenters/student_response_rate_presenter.rb @@ -0,0 +1,42 @@ +class StudentResponseRatePresenter < ResponseRatePresenter + def initialize(academic_year:, school:) + super(academic_year:, school:) + @survey_items = Measure.all.flat_map do |measure| + measure.student_survey_items_with_sufficient_responses(school:, academic_year:) + end + end + + def actual_count + # Early ed surveys are given in batches so they have to be counted separately because we have to account for the same student having a different response id per batch + non_early_ed_items = survey_items - SurveyItem.early_education_survey_items + non_early_ed_count = response_count_for_survey_items(survey_items: non_early_ed_items) + + early_ed_items = SurveyItem.early_education_survey_items + early_ed_count = SurveyItemResponse.where(school:, academic_year:, + survey_item: early_ed_items) + .group(:survey_item) + .select(:response_id) + .distinct + .count + .reduce(0) do |largest, row| + count = row[1] + if count > largest + count + else + largest + end + end + + non_early_ed_count + early_ed_count + end + + def respondents_count + return 0 if respondents.nil? + + enrollment + end + + def focus + "student" + end +end diff --git a/app/presenters/teacher_response_rate_presenter.rb b/app/presenters/teacher_response_rate_presenter.rb new file mode 100644 index 00000000..2144cba8 --- /dev/null +++ b/app/presenters/teacher_response_rate_presenter.rb @@ -0,0 +1,20 @@ +class TeacherResponseRatePresenter < ResponseRatePresenter + def initialize(academic_year:, school:) + super(academic_year:, school:) + @survey_items = SurveyItem.teacher_survey_items + end + + def actual_count + response_count_for_survey_items(survey_items:) + end + + def respondents_count + return 0 if respondents.nil? + + respondents.total_teachers + end + + def focus + "teacher" + end +end diff --git a/spec/controllers/overview_controller_spec.rb b/spec/controllers/overview_controller_spec.rb index 577ca11d..c1373641 100644 --- a/spec/controllers/overview_controller_spec.rb +++ b/spec/controllers/overview_controller_spec.rb @@ -1,4 +1,4 @@ -require 'rails_helper' +require "rails_helper" include VarianceHelper describe OverviewController, type: :controller do @@ -6,12 +6,12 @@ describe OverviewController, type: :controller do let(:school) { create(:school) } let(:district) { create(:district) } let!(:categories) do - [create(:category, name: 'Second', sort_index: 2), create(:category, name: 'First', sort_index: 1)] + [create(:category, name: "Second", sort_index: 2), create(:category, name: "First", sort_index: 1)] end - it 'fetches categories sorted by sort_index' do + it "fetches categories sorted by sort_index" do login_as district - get :index, params: { school_id: school.to_param, district_id: district.to_param } + get :index, params: { school_id: school.to_param, district_id: district.to_param } expect(assigns(:category_presenters).map(&:name)).to eql %w[First Second] end end diff --git a/spec/presenters/response_rate_presenter_spec.rb b/spec/presenters/response_rate_presenter_spec.rb index ebe3b0d6..d1c39546 100644 --- a/spec/presenters/response_rate_presenter_spec.rb +++ b/spec/presenters/response_rate_presenter_spec.rb @@ -57,7 +57,7 @@ describe ResponseRatePresenter do end it "ignores all teacher items and only gets the modified date of the last student item" do - date = ResponseRatePresenter.new(focus: :student, academic_year:, school:).date + date = StudentResponseRatePresenter.new(academic_year:, school:).date expect(date).to eq(newest_student_survey_response.recorded_date) end end @@ -70,7 +70,7 @@ describe ResponseRatePresenter do end it "ignores all student responses and only gets the modified date of the last teacher item" do - date = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).date + date = TeacherResponseRatePresenter.new(academic_year:, school:).date expect(date).to eq(newest_teacher_survey_response.recorded_date) end end @@ -83,7 +83,7 @@ describe ResponseRatePresenter do end context "when no survey responses are found for a school" do it "returns a response rate of 0" do - percentage = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).percentage + percentage = TeacherResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(0) end end @@ -95,7 +95,7 @@ describe ResponseRatePresenter do end it "returns a response rate of 100" do - percentage = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).percentage + percentage = TeacherResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(100) end end @@ -107,7 +107,7 @@ describe ResponseRatePresenter do end it "returns a response rate of 100" do - percentage = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).percentage + percentage = TeacherResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(100) end end @@ -119,7 +119,7 @@ describe ResponseRatePresenter do end it "returns a response rate of 75" do - percentage = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).percentage + percentage = TeacherResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(75) end end @@ -130,7 +130,7 @@ describe ResponseRatePresenter do end it "returns a response rate of 25" do - percentage = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).percentage + percentage = TeacherResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(25) end end @@ -141,7 +141,7 @@ describe ResponseRatePresenter do end it "its rounded to the nearest integer" do - percentage = ResponseRatePresenter.new(focus: :teacher, academic_year:, school:).percentage + percentage = TeacherResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(23) end end @@ -153,7 +153,7 @@ describe ResponseRatePresenter do end it "returns a response rate of 100" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(100) end end @@ -164,7 +164,7 @@ describe ResponseRatePresenter do end it "returns a response rate of 50" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(50) end end @@ -185,7 +185,7 @@ describe ResponseRatePresenter do survey_item: student_survey_item, grade: 1) end it "returns a response rate of 100" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(100) end end @@ -196,7 +196,7 @@ describe ResponseRatePresenter do survey_item: student_survey_item, grade: 1) end it "returns a response rate of 50" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(50) end end @@ -211,7 +211,7 @@ describe ResponseRatePresenter do survey_item: student_survey_item, grade: 2) end it "returns a response rate of 100" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(100) end end @@ -223,7 +223,7 @@ describe ResponseRatePresenter do survey_item: student_survey_item, grade: 2) end it "returns a response rate of 75" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(75) end end @@ -235,7 +235,7 @@ describe ResponseRatePresenter do survey_item: student_survey_item, grade: 2) end it "returns a response rate of 63 (rounded up from 62.5)" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(63) end end @@ -252,7 +252,7 @@ describe ResponseRatePresenter do survey_item: student_survey_item, grade: 3) end it "returns a response rate of 100" do - percentage = ResponseRatePresenter.new(focus: :student, academic_year:, school:).percentage + percentage = StudentResponseRatePresenter.new(academic_year:, school:).percentage expect(percentage).to eq(100) end end diff --git a/spec/presenters/variance_chart_row_presenter_spec.rb b/spec/presenters/variance_chart_row_presenter_spec.rb index 0aa92c70..5980455f 100644 --- a/spec/presenters/variance_chart_row_presenter_spec.rb +++ b/spec/presenters/variance_chart_row_presenter_spec.rb @@ -262,3 +262,4 @@ describe Overview::VarianceChartRowPresenter do end end end + diff --git a/spec/views/overview/index.html.erb_spec.rb b/spec/views/overview/index.html.erb_spec.rb index dc4b87c1..3248b7f0 100644 --- a/spec/views/overview/index.html.erb_spec.rb +++ b/spec/views/overview/index.html.erb_spec.rb @@ -73,10 +73,10 @@ describe "overview/index" do assign :page, Overview::OverviewPresenter.new(params: { view: "student" }, school: @school, academic_year: @academic_year) - @student_response_rate_presenter = ResponseRatePresenter.new(focus: :student, school: @school, - academic_year: @academic_year) - @teacher_response_rate_presenter = ResponseRatePresenter.new(focus: :teacher, school: @school, - academic_year: @academic_year) + @student_response_rate_presenter = StudentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @teacher_response_rate_presenter = TeacherResponseRatePresenter.new(school: @school, + academic_year: @academic_year) Respondent.create!(school: @school, academic_year: @academic_year, total_students: 40, total_teachers: 40) ResponseRate.create!(subcategory: Subcategory.first, school: @school, academic_year: @academic_year, @@ -111,10 +111,10 @@ describe "overview/index" do assign :page, Overview::OverviewPresenter.new(params: { view: "student" }, school: @school, academic_year: @academic_year) - @student_response_rate_presenter = ResponseRatePresenter.new(focus: :student, school: @school, - academic_year: @academic_year) - @teacher_response_rate_presenter = ResponseRatePresenter.new(focus: :teacher, school: @school, - academic_year: @academic_year) + @student_response_rate_presenter = StudentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @teacher_response_rate_presenter = TeacherResponseRatePresenter.new(school: @school, + academic_year: @academic_year) Respondent.create!(school: @school, academic_year: @academic_year, total_students: 40, total_teachers: 40) ResponseRate.create!(subcategory: Subcategory.first, school: @school, academic_year: @academic_year, @@ -150,10 +150,10 @@ describe "overview/index" do assign :page, Overview::OverviewPresenter.new(params: { view: "student" }, school: @school, academic_year: @academic_year) - @student_response_rate_presenter = ResponseRatePresenter.new(focus: :student, school: @school, - academic_year: @academic_year) - @teacher_response_rate_presenter = ResponseRatePresenter.new(focus: :teacher, school: @school, - academic_year: @academic_year) + @student_response_rate_presenter = StudentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @teacher_response_rate_presenter = TeacherResponseRatePresenter.new(school: @school, + academic_year: @academic_year) Respondent.create!(school: @school, academic_year: @academic_year, total_students: 40, total_teachers: 40) ResponseRate.create!(subcategory: Subcategory.first, school: @school, academic_year: @academic_year, @@ -181,10 +181,10 @@ describe "overview/index" do assign :page, Overview::OverviewPresenter.new(params: { view: "student" }, school: @school, academic_year: @academic_year) - @student_response_rate_presenter = ResponseRatePresenter.new(focus: :student, school: @school, - academic_year: @academic_year) - @teacher_response_rate_presenter = ResponseRatePresenter.new(focus: :teacher, school: @school, - academic_year: @academic_year) + @student_response_rate_presenter = StudentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @teacher_response_rate_presenter = TeacherResponseRatePresenter.new(school: @school, + academic_year: @academic_year) Respondent.create!(school: @school, academic_year: @academic_year, total_students: 40, total_teachers: 40) ResponseRate.create!(subcategory: Subcategory.first, school: @school, academic_year: @academic_year, @@ -217,10 +217,12 @@ describe "overview/index" do assign :page, Overview::ParentOverviewPresenter.new(params: { view: "parent" }, school: @school, academic_year: @academic_year) - @student_response_rate_presenter = ResponseRatePresenter.new(focus: :student, school: @school, - academic_year: @academic_year) - @teacher_response_rate_presenter = ResponseRatePresenter.new(focus: :teacher, school: @school, - academic_year: @academic_year) + @student_response_rate_presenter = StudentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @teacher_response_rate_presenter = TeacherResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @parent_response_rate_presenter = ParentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) Respondent.create!(school: @school, academic_year: @academic_year, total_students: 40, total_teachers: 40) ResponseRate.create!(subcategory: Subcategory.first, school: @school, academic_year: @academic_year, @@ -229,7 +231,7 @@ describe "overview/index" do assign(:category_presenters, Category.all.map { |category| CategoryPresenter.new(category:) }) render end - it "shows the view with the parent button active" do + it "shows the view with the parent button inactive" do expect(subject.css("input[id='parent_btn'][checked='checked']").count).to eq 0 expect(subject.css("input[id='student_and_teacher_btn'][checked='checked']").count).to eq 0 end @@ -247,11 +249,12 @@ describe "overview/index" do assign :page, Overview::ParentOverviewPresenter.new(params: { view: "parent" }, school: @school, academic_year: @academic_year) - @student_response_rate_presenter = ResponseRatePresenter.new(focus: :student, school: @school, - academic_year: @academic_year) - @teacher_response_rate_presenter = ResponseRatePresenter.new(focus: :teacher, school: @school, - academic_year: @academic_year) - + @student_response_rate_presenter = StudentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @teacher_response_rate_presenter = TeacherResponseRatePresenter.new(school: @school, + academic_year: @academic_year) + @parent_response_rate_presenter = ParentResponseRatePresenter.new(school: @school, + academic_year: @academic_year) Respondent.create!(school: @school, academic_year: @academic_year, total_students: 40, total_teachers: 40) ResponseRate.create!(subcategory: Subcategory.first, school: @school, academic_year: @academic_year, student_response_rate: 100, teacher_response_rate: 100, meets_student_threshold: true, meets_teacher_threshold: true) @@ -271,3 +274,4 @@ describe "overview/index" do end end end + diff --git a/spec/views/overview/variance_chart.html.erb_spec.rb b/spec/views/overview/variance_chart.html.erb_spec.rb index 9b1c646f..6f62e227 100644 --- a/spec/views/overview/variance_chart.html.erb_spec.rb +++ b/spec/views/overview/variance_chart.html.erb_spec.rb @@ -70,3 +70,4 @@ describe "overview/_variance_chart.html.erb" do end end end +