require "rails_helper" RSpec.describe SchemesController, type: :request do let(:organisation) { user.organisation } let(:headers) { { "Accept" => "text/html" } } let(:page) { Capybara::Node::Simple.new(response.body) } let(:user) { create(:user, :support) } let!(:schemes) { create_list(:scheme, 5) } before do schemes.each do |scheme| create(:location, scheme:) end end describe "#index" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider user" do let(:user) { create(:user) } before do sign_in user get "/schemes" end it "returns 200 success" do expect(response).to redirect_to(schemes_organisation_path(user.organisation.id)) end end context "when signed in as a data coordinator user" do let(:user) { create(:user, :data_coordinator) } before do schemes.each do |scheme| scheme.update!(owning_organisation: user.organisation) end sign_in user get "/schemes" end it "redirects to the organisation schemes path" do expect(response).to redirect_to(schemes_organisation_path(user.organisation.id)) end it "shows a list of schemes for the organisation" do follow_redirect! schemes.each do |scheme| expect(page).to have_content(scheme.id_to_display) end end context "when there are deleted schemes" do let!(:deleted_scheme) { create(:scheme, service_name: "deleted", discarded_at: Time.zone.yesterday, owning_organisation: user.organisation) } before do get "/schemes" end it "does not show deleted schemes" do follow_redirect! expect(page).not_to have_content(deleted_scheme.id_to_display) end end context "when parent organisation has schemes" do let(:parent_organisation) { create(:organisation) } let!(:parent_schemes) { create_list(:scheme, 5, owning_organisation: parent_organisation) } before do create(:organisation_relationship, parent_organisation:, child_organisation: user.organisation) parent_schemes.each do |scheme| create(:location, scheme:) end get "/schemes" end it "shows parent organisation schemes" do follow_redirect! parent_schemes.each do |scheme| expect(page).to have_content(scheme.id_to_display) end end end context "when a recently absorbed organisation has schemes" do let(:absorbed_org) { create(:organisation) } let!(:absorbed_org_schemes) { create_list(:scheme, 2, owning_organisation: absorbed_org) } before do absorbed_org.merge_date = 2.days.ago absorbed_org.absorbing_organisation = user.organisation absorbed_org.save! end it "shows absorbed organisation schemes" do get "/schemes" follow_redirect! absorbed_org_schemes.each do |scheme| expect(page).to have_content(scheme.id_to_display) end end end context "when a non-recently absorbed organisation has schemes" do let(:absorbed_org) { create(:organisation) } let!(:absorbed_org_schemes) { create_list(:scheme, 2, owning_organisation: absorbed_org) } before do absorbed_org.merge_date = 2.years.ago absorbed_org.absorbing_organisation = user.organisation absorbed_org.save! end it "shows absorbed organisation schemes" do get "/schemes" follow_redirect! absorbed_org_schemes.each do |scheme| expect(page).not_to have_content(scheme.id_to_display) end end end context "when filtering" do context "with owning organisation filter" do context "when user org does not have owning orgs or recently absorbed orgs" do it "does not show filter" do expect(page).not_to have_content("Owned by") end end context "when user org has owning orgs" do let!(:organisation1) { create(:organisation) } let!(:scheme1) { create(:scheme, owning_organisation: organisation1) } let!(:scheme2) { create(:scheme, owning_organisation: user.organisation) } before do org = user.organisation org.stock_owners = [organisation1, user.organisation] org.save! end context "when filtering by all owning orgs" do it "shows schemes for all owning orgs" do get "/schemes?owning_organisation_select=all", headers:, params: {} follow_redirect! expect(page).to have_content("Owned by") expect(page).to have_link(scheme1.service_name) expect(page).to have_link(scheme2.service_name) end end context "when filtering by an owning org" do it "when filtering by an owning org" do get "/schemes?owning_organisation=#{organisation1.id}", headers:, params: {} follow_redirect! expect(page).to have_content("Owned by") expect(page).to have_link(scheme1.service_name) expect(page).not_to have_link(scheme2.service_name) end end end end context "with status filter" do let!(:incomplete_scheme) { create(:scheme, :incomplete, owning_organisation: user.organisation) } let(:active_scheme) { create(:scheme, owning_organisation: user.organisation) } let!(:deactivated_scheme) { create(:scheme, owning_organisation: user.organisation) } before do create(:location, scheme: active_scheme) Timecop.freeze(Time.zone.local(2023, 11, 10)) create(:scheme_deactivation_period, scheme: deactivated_scheme, deactivation_date: Time.zone.local(2022, 4, 1)) Timecop.return end it "shows schemes for multiple selected statuses" do get "/schemes?status[]=incomplete&status[]=active", headers:, params: {} follow_redirect! expect(page).to have_link(incomplete_scheme.service_name) expect(page).to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end it "shows filtered incomplete schemes" do get "/schemes?status[]=incomplete", headers:, params: {} follow_redirect! expect(page).to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end it "shows filtered active schemes" do get "/schemes?status[]=active", headers:, params: {} follow_redirect! expect(page).to have_link(active_scheme.service_name) expect(page).not_to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end it "shows filtered deactivated schemes" do get "/schemes?status[]=deactivated", headers:, params: {} follow_redirect! expect(page).to have_link(deactivated_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(incomplete_scheme.service_name) end it "does not reset the filters" do get "/schemes?status[]=incomplete", headers:, params: {} follow_redirect! expect(page).to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) get "/schemes", headers:, params: {} follow_redirect! expect(page).to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end end end end context "when signed in as a support user" do before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes" end it "has page heading" do expect(page).to have_content("Schemes") end context "when there are deleted schemes" do let!(:deleted_scheme) { create(:scheme, service_name: "deleted", discarded_at: Time.zone.yesterday, owning_organisation: user.organisation) } before do get "/schemes" end it "does not show deleted schemes" do expect(page).not_to have_content(deleted_scheme.id_to_display) end end describe "scheme and location csv downloads" do let!(:same_org_scheme) { create(:scheme, owning_organisation: user.organisation) } let!(:specific_organisation) { create(:organisation) } let!(:specific_org_scheme) { create(:scheme, owning_organisation: specific_organisation) } before do create(:location, scheme: same_org_scheme) create_list(:scheme, 5, owning_organisation: specific_organisation) create_list(:location, 3, scheme: specific_org_scheme) end it "shows scheme and location download links" do expect(page).to have_link("Download schemes (CSV)", href: csv_download_schemes_path(download_type: "schemes")) expect(page).to have_link("Download locations (CSV)", href: csv_download_schemes_path(download_type: "locations")) expect(page).to have_link("Download schemes and locations (CSV)", href: csv_download_schemes_path(download_type: "combined")) end context "when there are no schemes for any organisation" do before do Scheme.destroy_all get "/schemes" end it "does not display CSV download links" do expect(page).not_to have_link("Download schemes (CSV)") expect(page).not_to have_link("Download locations (CSV)") expect(page).not_to have_link("Download schemes and locations (CSV)") end end context "when downloading scheme data" do before do get csv_download_schemes_path(download_type: "schemes") end it "redirects to the correct download page" do expect(page).to have_content("You've selected 12 schemes.") end end context "when downloading location data" do before do get csv_download_schemes_path(download_type: "locations") end it "redirects to the correct download page" do expect(page).to have_content("You've selected 9 locations from 12 schemes.") end end context "when downloading scheme and location data" do before do get csv_download_schemes_path(download_type: "combined") end it "redirects to the correct download page" do expect(page).to have_content("You've selected 12 schemes with 9 locations.") end end end it "shows all schemes" do schemes.each do |scheme| expect(page).to have_content(scheme.id_to_display) end end it "shows incomplete tag if the scheme is not confirmed" do schemes[0].update!(confirmed: nil) get "/schemes" assert_select ".govuk-tag", text: /Incomplete/, count: 1 end it "shows schemes in alphabetical order" do schemes[0].update!(service_name: "aaa") schemes[1].update!(service_name: "daa") schemes[2].update!(service_name: "baa") schemes[3].update!(service_name: "Faa") schemes[4].update!(service_name: "Caa") get "/schemes", headers:, params: {} all_links = page.all(".govuk-link") scheme_links = all_links.select { |link| link[:href] =~ %r{^/schemes/\d+$} } expect(scheme_links[0][:href]).to eq("/schemes/#{schemes[0].id}") expect(scheme_links[1][:href]).to eq("/schemes/#{schemes[2].id}") expect(scheme_links[2][:href]).to eq("/schemes/#{schemes[4].id}") expect(scheme_links[3][:href]).to eq("/schemes/#{schemes[1].id}") expect(scheme_links[4][:href]).to eq("/schemes/#{schemes[3].id}") end it "displays a link to check answers page if the scheme is incomplete" do scheme = schemes[0] scheme.update!(confirmed: nil) get "/schemes" expect(page).to have_link(nil, href: /schemes\/#{scheme.id}\/check-answers/) end it "shows a search bar" do expect(page).to have_field("search", type: "search") end it "has correct title" do expect(page).to have_title("Supported housing schemes - Submit social housing lettings and sales data (CORE) - GOV.UK") end it "shows the total organisations count" do expect(CGI.unescape_html(response.body)).to match("#{schemes.count} total schemes") end context "when paginating over 20 results" do let(:total_schemes_count) { Scheme.count } before do create_list(:scheme, 20) end context "when on the first page" do before do get "/schemes" end it "shows the total schemes count" do expect(CGI.unescape_html(response.body)).to match("#{total_schemes_count} total schemes") end it "shows which schemes are being shown on the current page" do expect(CGI.unescape_html(response.body)).to match("Showing 1 to 20 of #{total_schemes_count} schemes") end it "has correct page 1 of 2 title" do expect(page).to have_title("Supported housing schemes (page 1 of 2) - Submit social housing lettings and sales data (CORE) - GOV.UK") end it "has pagination links" do expect(page).not_to have_content("Previous") expect(page).not_to have_link("Previous") expect(page).to have_content("Next") expect(page).to have_link("Next") end end xcontext "when on the second page" do before do get "/schemes?page=2" end it "shows the total schemes count" do expect(CGI.unescape_html(response.body)).to match("#{total_schemes_count} total schemes") end it "has pagination links" do expect(page).to have_content("Previous") expect(page).to have_link("Previous") expect(page).not_to have_content("Next") expect(page).not_to have_link("Next") end it "shows which schemes are being shown on the current page" do expect(CGI.unescape_html(response.body)).to match("Showing 21 to 25 of #{total_schemes_count} schemes") end it "has correct page 1 of 2 title" do expect(page).to have_title("Supported housing schemes (page 2 of 2) - Submit social housing lettings and sales data (CORE) - GOV.UK") end end end context "when searching" do let!(:searched_scheme) { create(:scheme) } let(:search_param) { searched_scheme.id_to_display } before do create(:location, scheme: searched_scheme) get "/schemes?search=#{search_param}" end it "returns matching results" do expect(page).to have_content(searched_scheme.id_to_display) schemes.each do |scheme| expect(page).not_to have_content(scheme.id_to_display) end end it "returns results with no location" do scheme_without_location = create(:scheme) get "/schemes?search=#{scheme_without_location.id}" expect(page).to have_content(scheme_without_location.id_to_display) schemes.each do |scheme| expect(page).not_to have_content(scheme.id_to_display) end end it "updates the table caption" do expect(page).to have_content("1 scheme matching search") end it "has search in the title" do expect(page).to have_title("Supported housing schemes (1 scheme matching ‘#{search_param}’) - Submit social housing lettings and sales data (CORE) - GOV.UK") end end context "when filtering" do context "with owning organisation filter" do context "when user org does not have owning orgs" do it "shows the filter" do expect(page).to have_content("Owned by") end end context "when user org has owning orgs" do let!(:organisation1) { create(:organisation) } let!(:scheme1) { create(:scheme, owning_organisation: organisation1) } let!(:scheme2) { create(:scheme, owning_organisation: user.organisation) } context "when filtering by all owning orgs" do it "shows schemes for all owning orgs" do get "/schemes?owning_organisation_select=all", headers:, params: {} expect(page).to have_content("Owned by") expect(page).to have_link(scheme1.service_name) expect(page).to have_link(scheme2.service_name) end end context "when filtering by an owning org" do it "when filtering by an owning org" do get "/schemes?owning_organisation=#{organisation1.id}", headers:, params: {} expect(page).to have_content("Owned by") expect(page).to have_link(scheme1.service_name) expect(page).not_to have_link(scheme2.service_name) end end end end context "with status filter" do let!(:incomplete_scheme) { create(:scheme, :incomplete) } let(:active_scheme) { create(:scheme) } let!(:deactivated_scheme) { create(:scheme) } before do create(:location, scheme: active_scheme) Timecop.freeze(Time.zone.local(2023, 11, 10)) create(:scheme_deactivation_period, scheme: deactivated_scheme, deactivation_date: Time.zone.local(2022, 4, 1)) Timecop.return end it "shows schemes for multiple selected statuses" do get "/schemes?status[]=incomplete&status[]=active", headers:, params: {} expect(page).to have_link(incomplete_scheme.service_name) expect(page).to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end it "shows filtered incomplete schemes" do get "/schemes?status[]=incomplete", headers:, params: {} expect(page).to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end it "shows filtered active schemes" do get "/schemes?status[]=active", headers:, params: {} expect(page).to have_link(active_scheme.service_name) expect(page).not_to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end it "shows filtered deactivated schemes" do get "/schemes?status[]=deactivated", headers:, params: {} expect(page).to have_link(deactivated_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(incomplete_scheme.service_name) end it "does not reset the filters" do get "/schemes?status[]=incomplete", headers:, params: {} expect(page).to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) get "/schemes", headers:, params: {} expect(page).to have_link(incomplete_scheme.service_name) expect(page).not_to have_link(active_scheme.service_name) expect(page).not_to have_link(deactivated_scheme.service_name) end end end end end describe "#show" do let(:specific_scheme) { schemes.first } context "when not signed in" do it "redirects to the sign in page" do get "/schemes/#{specific_scheme.id}" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider user" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation) } before do sign_in user get "/schemes/#{scheme.id}" end it "returns 200" do expect(response).to be_successful end end context "when signed in as a data coordinator user" do let(:user) { create(:user, :data_coordinator) } let!(:specific_scheme) { create(:scheme, owning_organisation: user.organisation) } before do sign_in user end it "has page heading" do get "/schemes/#{specific_scheme.id}" expect(page).to have_content(specific_scheme.id_to_display) expect(page).to have_content(specific_scheme.service_name) expect(page).to have_content(specific_scheme.sensitive) expect(page).to have_content(specific_scheme.scheme_type) expect(page).to have_content(specific_scheme.registered_under_care_act) expect(page).to have_content(specific_scheme.primary_client_group) expect(page).to have_content(specific_scheme.secondary_client_group) expect(page).to have_content(specific_scheme.support_type) expect(page).to have_content(specific_scheme.intended_stay) end context "when coordinator attempts to see scheme belonging to a different (and not their parent) organisation" do let!(:specific_scheme) { create(:scheme) } it "returns 401" do get "/schemes/#{specific_scheme.id}" expect(response).to be_unauthorized end end context "when the requested scheme does not exist" do it "returns not found" do get "/schemes/#{Scheme.maximum(:id) + 1}" expect(response).to have_http_status(:not_found) end end context "when looking at scheme details" do let!(:scheme) { create(:scheme, owning_organisation: user.organisation) } let(:add_deactivations) { scheme.scheme_deactivation_periods << scheme_deactivation_period } before do create(:location, scheme:) Timecop.freeze(Time.utc(2022, 10, 10)) sign_in user add_deactivations scheme.save! get "/schemes/#{scheme.id}" end after do Timecop.unfreeze end context "with active scheme" do let(:add_deactivations) {} it "renders deactivate this scheme" do expect(response).to have_http_status(:ok) expect(page).to have_link("Deactivate this scheme", href: "/schemes/#{scheme.id}/new-deactivation") end end context "with deactivated scheme" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 9), scheme:) } it "renders reactivate this scheme" do expect(response).to have_http_status(:ok) expect(page).to have_link("Reactivate this scheme", href: "/schemes/#{scheme.id}/new-reactivation") end it "does not render delete this scheme" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end end context "with scheme that's deactivating soon" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 12), scheme:) } it "does render the reactivate this scheme button" do expect(response).to have_http_status(:ok) expect(page).to have_link("Reactivate this scheme") expect(page).not_to have_link("Deactivate this scheme") end end context "with scheme that's deactivating in more than 6 months" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 5, 12), scheme:) } it "does not render toggle scheme link" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Reactivate this scheme") expect(page).to have_link("Deactivate this scheme") expect(response.body).not_to include("Deactivating soon") expect(response.body).to include("Active") end end end context "when coordinator attempts to see scheme belonging to a parent organisation" do let(:parent_organisation) { create(:organisation) } let!(:specific_scheme) { create(:scheme, owning_organisation: parent_organisation) } let(:add_deactivations) { specific_scheme.scheme_deactivation_periods << scheme_deactivation_period } before do create(:location, scheme: specific_scheme) create(:organisation_relationship, parent_organisation:, child_organisation: user.organisation) Timecop.freeze(Time.utc(2022, 10, 10)) sign_in user add_deactivations specific_scheme.save! get "/schemes/#{specific_scheme.id}" end after do Timecop.unfreeze end context "with active scheme" do let(:add_deactivations) {} it "shows the scheme" do expect(page).to have_content(specific_scheme.id_to_display) end it "allows editing" do expect(page).to have_link("Change") end it "renders deactivate this scheme" do expect(response).to have_http_status(:ok) expect(page).to have_link("Deactivate this scheme", href: "/schemes/#{specific_scheme.id}/new-deactivation") end end context "with deactivated scheme" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 9), scheme: specific_scheme) } it "renders reactivate this scheme" do expect(response).to have_http_status(:ok) expect(page).to have_link("Reactivate this scheme", href: "/schemes/#{specific_scheme.id}/new-reactivation") end end context "with scheme that's deactivating soon" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 12), scheme: specific_scheme) } it "does render the reactivate this scheme button" do expect(response).to have_http_status(:ok) expect(page).to have_link("Reactivate this scheme") expect(page).not_to have_link("Deactivate this scheme") end end context "with scheme that's deactivating in more than 6 months" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 5, 12), scheme: specific_scheme) } it "does not render toggle scheme link" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Reactivate this scheme") expect(page).to have_link("Deactivate this scheme") expect(response.body).not_to include("Deactivating soon") expect(response.body).to include("Active") end end end context "when coordinator attempts to see scheme belonging to a recently absorbed organisation" do let(:absorbed_organisation) { create(:organisation) } let!(:specific_scheme) { create(:scheme, owning_organisation: absorbed_organisation) } before do absorbed_organisation.merge_date = 2.days.ago absorbed_organisation.absorbing_organisation = user.organisation absorbed_organisation.save! get "/schemes/#{specific_scheme.id}" end it "shows the scheme" do expect(page).to have_content(specific_scheme.id_to_display) end it "allows editing" do expect(page).to have_link("Change") end end context "when the scheme has all details but no confirmed locations" do it "shows the scheme as incomplete with text to explain" do get scheme_path(specific_scheme) expect(page).to have_content "Incomplete" expect(page).to have_content "Complete this scheme by adding a location using the" expect(page).to have_link "‘locations’ tab" end end context "when the scheme has all details and confirmed locations" do it "shows the scheme as complete" do create(:location, scheme: specific_scheme) get scheme_path(specific_scheme) expect(page).to have_content "Active" expect(page).not_to have_content "Complete this scheme by adding a location using the" expect(page).not_to have_link "‘locations’ tab" end end end context "when signed in as a support user" do before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{specific_scheme.id}" end it "has page heading" do expect(page).to have_content(specific_scheme.id_to_display) expect(page).to have_content(specific_scheme.service_name) expect(page).to have_content(specific_scheme.owning_organisation.name) expect(page).to have_content(specific_scheme.sensitive) expect(page).to have_content(specific_scheme.id_to_display) expect(page).to have_content(specific_scheme.service_name) expect(page).to have_content(specific_scheme.sensitive) expect(page).to have_content(specific_scheme.scheme_type) expect(page).to have_content(specific_scheme.registered_under_care_act) expect(page).to have_content(specific_scheme.primary_client_group) expect(page).to have_content(specific_scheme.secondary_client_group) expect(page).to have_content(specific_scheme.support_type) expect(page).to have_content(specific_scheme.intended_stay) end context "when looking at scheme details" do let!(:scheme) { create(:scheme, owning_organisation: user.organisation) } let(:add_deactivations) { scheme.scheme_deactivation_periods << scheme_deactivation_period } before do create(:location, scheme:) Timecop.freeze(Time.utc(2022, 10, 10)) sign_in user add_deactivations scheme.save! get "/schemes/#{scheme.id}" end after do Timecop.unfreeze end context "with active scheme" do let(:add_deactivations) {} it "does not render delete this scheme" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end it "does not render informative text about deleting the scheme" do expect(response).to have_http_status(:ok) expect(page).not_to have_content("This scheme was active in an open or editable collection year, and cannot be deleted.") end end context "with deactivated scheme" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 9), scheme:) } it "renders delete this scheme" do expect(response).to have_http_status(:ok) expect(page).to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end context "and associated logs in editable collection period" do before do create(:location, scheme:) create(:lettings_log, :sh, scheme:, startdate: Time.zone.local(2022, 9, 9), owning_organisation: user.organisation) get "/schemes/#{scheme.id}" end it "does not render delete this scheme" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end it "adds informative text about deleting the scheme" do expect(response).to have_http_status(:ok) expect(page).to have_content("This scheme was active in an open or editable collection year, and cannot be deleted.") end end end context "with scheme that's deactivating soon" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 12), scheme:) } it "does not render delete this scheme" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end end context "with scheme that's deactivating in more than 6 months" do let(:scheme_deactivation_period) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 5, 12), scheme:) } it "does not render delete this scheme" do expect(response).to have_http_status(:ok) expect(page).not_to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end end context "with incomplete scheme" do let(:add_deactivations) {} let!(:scheme) { create(:scheme, :incomplete, owning_organisation: user.organisation) } it "renders delete this scheme" do expect(response).to have_http_status(:ok) expect(page).to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end end end end end describe "#new" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/new" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } before do sign_in user get "/schemes/new" end it "returns 401" do expect(response).to be_unauthorized end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } before do sign_in user get "/schemes/new" end it "returns a template for a new scheme" do expect(response).to have_http_status(:ok) expect(page).to have_content("Create a new supported housing scheme") end end context "when signed in as a support user" do let(:user) { create(:user, :support) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/new" end it "returns a template for a new scheme" do expect(response).to have_http_status(:ok) expect(page).to have_content("Create a new supported housing scheme") end end end describe "#create" do context "when not signed in" do it "redirects to the sign in page" do post "/schemes" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:params) do { scheme: { service_name: "asd", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", arrangement_type: "D" } } end before do sign_in user post "/schemes", params: end it "returns 401" do expect(response).to have_http_status(:unauthorized) end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } before do sign_in user end context "when making a scheme in the user's organisation" do let!(:params) do { scheme: { service_name: " testy ", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: user.organisation.id, arrangement_type: "D" } } end it "creates a new scheme for user organisation with valid params and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end it "creates a new scheme for user organisation with valid params" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation_id) expect(Scheme.last.service_name).to eq("testy") expect(Scheme.last.scheme_type).to eq("Foyer") expect(Scheme.last.sensitive).to eq("Yes") expect(Scheme.last.registered_under_care_act).to eq("No") expect(Scheme.last.id).not_to eq(nil) expect(Scheme.last.has_other_client_group).to eq(nil) expect(Scheme.last.primary_client_group).to eq(nil) expect(Scheme.last.secondary_client_group).to eq(nil) expect(Scheme.last.support_type).to eq(nil) expect(Scheme.last.intended_stay).to eq(nil) expect(Scheme.last.id_to_display).to match(/S*/) end context "when support services provider is selected" do let(:params) do { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: user.organisation.id, arrangement_type: "R" } } end it "creates a new scheme for user organisation with valid params and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content(" What client group is this scheme intended for?") end it "creates a new scheme for user organisation with valid params" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation_id) expect(Scheme.last.service_name).to eq("testy") expect(Scheme.last.scheme_type).to eq("Foyer") expect(Scheme.last.sensitive).to eq("Yes") expect(Scheme.last.registered_under_care_act).to eq("No") expect(Scheme.last.id).not_to eq(nil) expect(Scheme.last.has_other_client_group).to eq(nil) expect(Scheme.last.primary_client_group).to eq(nil) expect(Scheme.last.secondary_client_group).to eq(nil) expect(Scheme.last.support_type).to eq(nil) expect(Scheme.last.intended_stay).to eq(nil) expect(Scheme.last.id_to_display).to match(/S*/) end end context "when required params are missing" do let(:params) do { scheme: { service_name: "", scheme_type: "", registered_under_care_act: "", arrangement_type: "" } } end it "renders the same page with error message" do post "/schemes", params: params expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content("Create a new supported housing scheme") expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.scheme_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.registered_under_care_act.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.arrangement_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.service_name.invalid")) end end context "when there are no stock owners" do let(:params) do { scheme: { service_name: " testy ", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", arrangement_type: "D" } } end before do user.organisation.stock_owners.destroy_all end it "infers the user's organisation" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation_id) end end context "when the organisation id param is included" do let(:organisation) { create(:organisation) } let(:params) { { scheme: { owning_organisation: organisation } } } it "sets the owning organisation correctly" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation_id) end end end context "when making a scheme in a parent organisation of the user's organisation" do let(:parent_organisation) { create(:organisation) } let!(:parent_schemes) { create_list(:scheme, 5, owning_organisation: parent_organisation) } let(:params) do { scheme: { service_name: " testy ", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: user.organisation.stock_owners.first.id, arrangement_type: "D" } } end before do create(:organisation_relationship, parent_organisation:, child_organisation: user.organisation) parent_schemes.each do |scheme| create(:location, scheme:) end end it "creates a new scheme for user organisation with valid params and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end it "creates a new scheme for user organisation with valid params" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation.stock_owners.first.id) expect(Scheme.last.service_name).to eq("testy") expect(Scheme.last.scheme_type).to eq("Foyer") expect(Scheme.last.sensitive).to eq("Yes") expect(Scheme.last.registered_under_care_act).to eq("No") expect(Scheme.last.id).not_to eq(nil) expect(Scheme.last.has_other_client_group).to eq(nil) expect(Scheme.last.primary_client_group).to eq(nil) expect(Scheme.last.secondary_client_group).to eq(nil) expect(Scheme.last.support_type).to eq(nil) expect(Scheme.last.intended_stay).to eq(nil) expect(Scheme.last.id_to_display).to match(/S*/) end context "when support services provider is selected" do let(:params) do { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: user.organisation.stock_owners.first.id, arrangement_type: "R" } } end it "creates a new scheme for user organisation with valid params and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content(" What client group is this scheme intended for?") end it "creates a new scheme for user organisation with valid params" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation.stock_owners.first.id) expect(Scheme.last.service_name).to eq("testy") expect(Scheme.last.scheme_type).to eq("Foyer") expect(Scheme.last.sensitive).to eq("Yes") expect(Scheme.last.registered_under_care_act).to eq("No") expect(Scheme.last.id).not_to eq(nil) expect(Scheme.last.has_other_client_group).to eq(nil) expect(Scheme.last.primary_client_group).to eq(nil) expect(Scheme.last.secondary_client_group).to eq(nil) expect(Scheme.last.support_type).to eq(nil) expect(Scheme.last.intended_stay).to eq(nil) expect(Scheme.last.id_to_display).to match(/S*/) end end context "when required params are missing" do let(:params) do { scheme: { service_name: "", scheme_type: "", registered_under_care_act: "", arrangement_type: "", owning_organisation_id: "" } } end it "renders the same page with error message" do post "/schemes", params: params expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content("Create a new supported housing scheme") expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.scheme_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.registered_under_care_act.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.arrangement_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.owning_organisation_id.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.service_name.invalid")) end end context "when the organisation id param is included" do let(:organisation) { create(:organisation) } let(:params) { { scheme: { owning_organisation: organisation } } } it "sets the owning organisation correctly" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(user.organisation.stock_owners.first.id) end end end context "when making a scheme in an organisation recently absorbed by the users organisation" do let(:absorbed_organisation) { create(:organisation) } let(:params) do { scheme: { service_name: " testy ", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: absorbed_organisation.id, arrangement_type: "D" } } end before do absorbed_organisation.merge_date = 2.days.ago absorbed_organisation.absorbing_organisation = user.organisation absorbed_organisation.save! end it "creates a new scheme for this organisation and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end end end context "when signed in as a support user" do let(:organisation) { create(:organisation) } let(:user) { create(:user, :support) } let(:params) do { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: organisation.id, arrangement_type: "D" } } end before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user end it "creates a new scheme for user organisation with valid params and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end it "creates a new scheme for user organisation with valid params" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(organisation.id) expect(Scheme.last.service_name).to eq("testy") expect(Scheme.last.scheme_type).to eq("Foyer") expect(Scheme.last.sensitive).to eq("Yes") expect(Scheme.last.registered_under_care_act).to eq("No") expect(Scheme.last.id).not_to eq(nil) expect(Scheme.last.has_other_client_group).to eq(nil) expect(Scheme.last.primary_client_group).to eq(nil) expect(Scheme.last.secondary_client_group).to eq(nil) expect(Scheme.last.support_type).to eq(nil) expect(Scheme.last.intended_stay).to eq(nil) expect(Scheme.last.id_to_display).to match(/S*/) end context "when support services provider is selected" do let(:params) do { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", owning_organisation_id: organisation.id, support_services_provider_before_type_cast: "1" } } end it "creates a new scheme for user organisation with valid params and renders correct page" do expect { post "/schemes", params: }.to change(Scheme, :count).by(1) follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end it "creates a new scheme for user organisation with valid params" do post "/schemes", params: params expect(Scheme.last.owning_organisation_id).to eq(organisation.id) expect(Scheme.last.service_name).to eq("testy") expect(Scheme.last.scheme_type).to eq("Foyer") expect(Scheme.last.sensitive).to eq("Yes") expect(Scheme.last.registered_under_care_act).to eq("No") expect(Scheme.last.id).not_to eq(nil) expect(Scheme.last.has_other_client_group).to eq(nil) expect(Scheme.last.primary_client_group).to eq(nil) expect(Scheme.last.secondary_client_group).to eq(nil) expect(Scheme.last.support_type).to eq(nil) expect(Scheme.last.intended_stay).to eq(nil) expect(Scheme.last.id_to_display).to match(/S*/) end end context "when required params are missing" do let(:params) do { scheme: { service_name: "", scheme_type: "", registered_under_care_act: "", owning_organisation_id: nil, arrangement_type: "" } } end it "renders the same page with error message" do post "/schemes", params: params expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content("Create a new supported housing scheme") expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.scheme_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.registered_under_care_act.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.arrangement_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.service_name.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.owning_organisation_id.invalid")) end end context "when organisation id param refers to a non-stock-owning organisation" do let(:organisation_which_does_not_own_stock) { create(:organisation, holds_own_stock: false) } let(:params) { { scheme: { owning_organisation_id: organisation_which_does_not_own_stock.id } } } it "displays the new page with an error message" do post "/schemes", params: params expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content("Enter an organisation that owns housing stock") end end end end describe "#update" do context "when not signed in" do it "redirects to the sign in page" do patch "/schemes/#{schemes.first.id}" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } before do sign_in user patch "/schemes/#{schemes.first.id}" end it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let(:scheme_to_update) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do sign_in user patch "/schemes/#{scheme_to_update.id}", params: end context "when confirming unfinished scheme" do let(:params) { { scheme: { owning_organisation_id: user.organisation.id, arrangement_type: nil, confirmed: true, page: "check-answers" } } } it "does not allow the scheme to be confirmed" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.arrangement_type.invalid")) end end context "when scheme is completed but not yet confirmed" do let(:params) { { scheme: { page: "check-answers" } } } it "is not confirmed" do expect(scheme_to_update.confirmed).to eq(nil) end context "when confirming finished scheme" do let(:params) { { scheme: { confirmed: true, page: "check-answers" } } } before do scheme_to_update.reload end it "confirms scheme" do expect(scheme_to_update.confirmed).to eq(true) end end end context "when required params are missing" do let(:params) do { scheme: { service_name: "", primary_client_group: "", secondary_client_group: "", scheme_type: "", registered_under_care_act: "", support_type: "", intended_stay: "", arrangement_type: "", has_other_client_group: "", page: "details", } } end it "renders the same page with error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content("Create a new supported housing scheme") expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.service_name.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.scheme_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.registered_under_care_act.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.primary_client_group.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.secondary_client_group.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.support_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.intended_stay.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.has_other_client_group.invalid")) end context "when updating from check answers page" do let(:params) { { scheme: { primary_client_group: "Homeless families with support needs", page: "primary-client-group", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.primary_client_group).to eq("Homeless families with support needs") end end end context "when updating primary client group" do let(:params) { { scheme: { primary_client_group: "Homeless families with support needs", page: "primary-client-group" } } } it "renders confirm secondary group after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Does this scheme provide for another client group?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.primary_client_group).to eq("Homeless families with support needs") end context "when updating from check answers page" do let(:params) { { scheme: { primary_client_group: "Homeless families with support needs", page: "primary-client-group", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.primary_client_group).to eq("Homeless families with support needs") end end end context "when updating confirm secondary client group" do let(:params) { { scheme: { has_other_client_group: "Yes", page: "confirm-secondary" } } } it "renders secondary client group after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What is the other client group?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("Yes") end context "when updating from check answers page with the answer YES and no secondary client group set" do let(:scheme_to_update) { create(:scheme, owning_organisation: user.organisation, confirmed: nil, secondary_client_group: nil) } let(:params) { { scheme: { has_other_client_group: "Yes", page: "confirm-secondary", check_answers: "true" } } } it "renders secondary client group page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What is the other client group?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("Yes") end end context "when updating from check answers page with the answer YES and a secondary client group set" do let(:scheme_to_update) { create(:scheme, owning_organisation: user.organisation, confirmed: nil, secondary_client_group: "F") } let(:params) { { scheme: { has_other_client_group: "Yes", page: "confirm-secondary", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("Yes") end end context "when updating from check answers page with the answer NO" do let(:params) { { scheme: { has_other_client_group: "No", page: "confirm-secondary", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("No") end end end context "when updating secondary client group" do let(:params) { { scheme: { secondary_client_group: "Homeless families with support needs", page: "secondary-client-group" } } } it "renders confirm support page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What support does this scheme provide?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.secondary_client_group).to eq("Homeless families with support needs") end context "when updating from check answers page" do let(:params) { { scheme: { secondary_client_group: "Homeless families with support needs", page: "secondary-client-group", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.secondary_client_group).to eq("Homeless families with support needs") end end end context "when updating support" do let(:params) { { scheme: { intended_stay: "Medium stay", support_type: "Low level", page: "support" } } } it "renders the check answers page" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your answers before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.intended_stay).to eq("Medium stay") expect(scheme_to_update.reload.support_type).to eq("Low level") end context "when updating from check answers page" do let(:params) { { scheme: { intended_stay: "Medium stay", support_type: "Low level", page: "support", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.intended_stay).to eq("Medium stay") expect(scheme_to_update.reload.support_type).to eq("Low level") end end end context "when updating details" do let(:params) do { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", page: "details", owning_organisation_id: organisation.id, arrangement_type: "D" } } end it "renders confirm secondary group after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.service_name).to eq("testy") expect(scheme_to_update.reload.scheme_type).to eq("Foyer") expect(scheme_to_update.reload.sensitive).to eq("Yes") expect(scheme_to_update.reload.registered_under_care_act).to eq("No") end context "when updating from check answers page" do let(:params) { { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", page: "details", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.service_name).to eq("testy") expect(scheme_to_update.reload.scheme_type).to eq("Foyer") expect(scheme_to_update.reload.sensitive).to eq("Yes") expect(scheme_to_update.reload.registered_under_care_act).to eq("No") end end end context "when editing scheme name details" do let(:params) { { scheme: { service_name: "testy", sensitive: "1", page: "edit-name" } } } it "renders scheme show page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content(scheme_to_update.reload.service_name) end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.service_name).to eq("testy") expect(scheme_to_update.reload.sensitive).to eq("Yes") end end context "when the requested scheme does not exist" do let(:scheme_to_update) { OpenStruct.new(id: Scheme.maximum(:id) + 1) } let(:params) { {} } it "returns not found" do expect(response).to have_http_status(:not_found) end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let(:scheme_to_update) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do create(:location, scheme: scheme_to_update) allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user patch "/schemes/#{scheme_to_update.id}", params: end context "when confirming unfinished scheme" do let(:params) { { scheme: { owning_organisation_id: user.organisation.id, arrangement_type: nil, confirmed: true, page: "check-answers" } } } it "does not allow the scheme to be confirmed" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.arrangement_type.invalid")) end end context "when scheme is completed but not yet confirmed" do let(:params) { { scheme: { page: "check-answers" } } } it "is not confirmed" do expect(scheme_to_update.confirmed).to eq(nil) end context "when confirming finished scheme" do let(:params) { { scheme: { confirmed: true, page: "check-answers" } } } before do scheme_to_update.reload end it "confirms scheme" do expect(scheme_to_update.confirmed).to eq(true) end end end context "when required params are missing" do let(:params) do { scheme: { service_name: "", managing_organisation_id: "", owning_organisation_id: "", primary_client_group: "", secondary_client_group: "", scheme_type: "", registered_under_care_act: "", support_type: "", intended_stay: "", arrangement_type: "", has_other_client_group: "", page: "details", } } end it "renders the same page with error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content("Create a new supported housing scheme") expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.owning_organisation_id.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.service_name.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.scheme_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.registered_under_care_act.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.primary_client_group.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.secondary_client_group.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.support_type.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.intended_stay.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.has_other_client_group.invalid")) expect(page).to have_content(I18n.t("activerecord.errors.models.scheme.attributes.arrangement_type.invalid")) end context "when updating from check answers page" do let(:params) { { scheme: { primary_client_group: "Homeless families with support needs", page: "primary-client-group", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.primary_client_group).to eq("Homeless families with support needs") end end context "when saving a scheme" do let(:params) { { scheme: { page: "check-answers", confirmed: "true" } } } it "marks the scheme as confirmed" do expect(scheme_to_update.reload.confirmed?).to eq(true) end it "marks all the scheme locations as confirmed given they are complete" do expect(scheme_to_update.locations.count > 0).to eq(true) scheme_to_update.locations.each do |location| expect(location.confirmed?).to eq(true) end end end end context "when updating primary client group" do let(:params) { { scheme: { primary_client_group: "Homeless families with support needs", page: "primary-client-group" } } } it "renders confirm secondary group after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Does this scheme provide for another client group?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.primary_client_group).to eq("Homeless families with support needs") end context "when updating from check answers page" do let(:params) { { scheme: { primary_client_group: "Homeless families with support needs", page: "primary-client-group", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.primary_client_group).to eq("Homeless families with support needs") end end end context "when updating confirm secondary client group" do let(:params) { { scheme: { has_other_client_group: "Yes", page: "confirm-secondary" } } } it "renders secondary client group after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What is the other client group?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("Yes") end context "when updating from check answers page with the answer YES and no existing secondary client group set" do let(:scheme_to_update) { create(:scheme, owning_organisation: user.organisation, confirmed: nil, secondary_client_group: nil) } let(:params) { { scheme: { has_other_client_group: "Yes", page: "confirm-secondary", check_answers: "true" } } } it "renders secondary client group page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What is the other client group?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("Yes") end end context "when updating from check answers page with the answer YES and an existing secondary client group set" do let(:scheme_to_update) { create(:scheme, owning_organisation: user.organisation, confirmed: nil, secondary_client_group: "F") } let(:params) { { scheme: { has_other_client_group: "Yes", page: "confirm-secondary", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("Yes") end end context "when updating from check answers page with the answer NO" do let(:params) { { scheme: { has_other_client_group: "No", page: "confirm-secondary", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.has_other_client_group).to eq("No") end end end context "when updating secondary client group" do let(:params) { { scheme: { secondary_client_group: "Homeless families with support needs", page: "secondary-client-group" } } } it "renders confirm support page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What support does this scheme provide?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.secondary_client_group).to eq("Homeless families with support needs") end context "when updating from check answers page" do let(:params) { { scheme: { secondary_client_group: "Homeless families with support needs", page: "secondary-client-group", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.secondary_client_group).to eq("Homeless families with support needs") end end end context "when updating support" do let(:params) { { scheme: { intended_stay: "Medium stay", support_type: "Low level", page: "support" } } } it "renders scheme check your answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your answers before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.intended_stay).to eq("Medium stay") expect(scheme_to_update.reload.support_type).to eq("Low level") end context "when updating from check answers page" do let(:params) { { scheme: { intended_stay: "Medium stay", support_type: "Low level", page: "support", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.intended_stay).to eq("Medium stay") expect(scheme_to_update.reload.support_type).to eq("Low level") end end end context "when updating details" do let(:another_organisation) { create(:organisation) } let(:params) do { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", page: "details", arrangement_type: "The same organisation that owns the housing stock", owning_organisation_id: another_organisation.id } } end it "renders confirm secondary group after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.service_name).to eq("testy") expect(scheme_to_update.reload.scheme_type).to eq("Foyer") expect(scheme_to_update.reload.sensitive).to eq("Yes") expect(scheme_to_update.reload.registered_under_care_act).to eq("No") expect(scheme_to_update.reload.owning_organisation_id).to eq(another_organisation.id) end context "when updating from check answers page" do let(:params) { { scheme: { service_name: "testy", sensitive: "1", scheme_type: "Foyer", registered_under_care_act: "No", page: "details", check_answers: "true" } } } it "renders check answers page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.service_name).to eq("testy") expect(scheme_to_update.reload.scheme_type).to eq("Foyer") expect(scheme_to_update.reload.sensitive).to eq("Yes") expect(scheme_to_update.reload.registered_under_care_act).to eq("No") end end end context "when editing scheme name details" do let(:another_organisation) { create(:organisation) } let(:params) do { scheme: { service_name: "testy", sensitive: "1", page: "edit-name", owning_organisation_id: another_organisation.id } } end it "renders scheme show page after successful update" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content(scheme_to_update.reload.service_name) expect(scheme_to_update.reload.owning_organisation_id).to eq(another_organisation.id) end it "updates a scheme with valid params" do follow_redirect! expect(scheme_to_update.reload.service_name).to eq("testy") expect(scheme_to_update.reload.sensitive).to eq("Yes") end end end end describe "#primary_client_group" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/primary-client-group" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/primary-client-group" end it "returns 401" do expect(response).to be_unauthorized end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } let(:another_scheme) { create(:scheme, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/primary-client-group" end it "returns a template for a primary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end context "when attempting to access primary-client-group scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/primary-client-group" end it "returns 401" do expect(response).to be_unauthorized end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme, confirmed: nil) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/primary-client-group" end it "returns a template for a primary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("What client group is this scheme intended for?") end context "and the scheme is confirmed" do before do scheme.update!(confirmed: true) get "/schemes/#{scheme.id}/primary-client-group" end it "allows editing the primary client group" do expect(response).to have_http_status(:ok) expect(path).to match("/schemes/#{scheme.id}/primary-client-group") end end end end describe "#confirm_secondary_client_group" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/confirm-secondary-client-group" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/confirm-secondary-client-group" end it "returns 401" do expect(response).to be_unauthorized end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } let(:another_scheme) { create(:scheme, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/confirm-secondary-client-group" end it "returns a template for a confirm-secondary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("Does this scheme provide for another client group?") end context "when attempting to access confirm-secondary-client-group scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/confirm-secondary-client-group" end it "returns 401" do expect(response).to be_unauthorized end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme, confirmed: nil) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/confirm-secondary-client-group" end it "returns a template for a confirm-secondary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("Does this scheme provide for another client group?") end context "and the scheme is confirmed" do before do scheme.update!(confirmed: true) get "/schemes/#{scheme.id}/confirm-secondary-client-group" end it "allows updating secondary client group" do expect(response).to have_http_status(:ok) expect(path).to match("/schemes/#{scheme.id}/confirm-secondary-client-group") end end end end describe "#secondary_client_group" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/secondary-client-group" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/secondary-client-group" end it "returns 401" do expect(response).to be_unauthorized end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } let(:another_scheme) { create(:scheme, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/secondary-client-group" end it "returns a template for a secondary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("What is the other client group?") end context "when attempting to access secondary-client-group scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/secondary-client-group" end it "returns 401" do expect(response).to be_unauthorized end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme, confirmed: nil, primary_client_group: Scheme::PRIMARY_CLIENT_GROUP[:"Homeless families with support needs"]) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/secondary-client-group" end it "returns a template for a secondary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("What is the other client group?") end context "and the scheme is confirmed" do before do scheme.update!(confirmed: true) get "/schemes/#{scheme.id}/secondary-client-group" end it "allows editing secondary client group" do expect(response).to have_http_status(:ok) expect(path).to match("/schemes/#{scheme.id}/secondary-client-group") end end it "does not show the primary client group as an option" do expect(scheme.primary_client_group).not_to be_nil expect(page).not_to have_content("Homeless families with support needs") end end end describe "#support" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/support" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/support" end it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } let(:another_scheme) { create(:scheme, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/support" end it "returns a template for a support" do expect(response).to have_http_status(:ok) expect(page).to have_content("What support does this scheme provide?") end context "when attempting to access secondary-client-group scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/support" end it "returns 401" do expect(response).to be_unauthorized end end context "and the scheme is confirmed" do before do scheme.update!(confirmed: true) get "/schemes/#{scheme.id}/support" end it "redirects to a view scheme page" do follow_redirect! expect(response).to have_http_status(:ok) expect(path).to match("/schemes/#{scheme.id}") expect(page).to have_content(scheme.service_name) assert_select "a", text: /Change/, count: 3 end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme, confirmed: nil) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/support" end it "returns a template for a support" do expect(response).to have_http_status(:ok) expect(page).to have_content("What support does this scheme provide?") end end end describe "#check-answers" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/check-answers" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation) } before do sign_in user get "/schemes/#{scheme.id}/check-answers" end it "returns 200" do expect(response).to be_successful end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let!(:scheme) { create(:scheme, owning_organisation: user.organisation) } let!(:another_scheme) { create(:scheme) } before do sign_in user get "/schemes/#{scheme.id}/check-answers" end it "returns a template for a support" do expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end context "when attempting to access check-answers scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/check-answers" end it "returns 401" do expect(response).to be_unauthorized end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme) } before do create(:location, scheme:) allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/check-answers" end it "returns a template for a support" do expect(response).to have_http_status(:ok) expect(page).to have_content("Check your changes before creating this scheme") end context "with an active scheme" do it "does not render delete this scheme" do expect(scheme.status).to eq(:active) expect(page).not_to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end end context "with an incomplete scheme" do let(:scheme) { create(:scheme, :incomplete) } it "renders delete this scheme" do expect(scheme.reload.status).to eq(:incomplete) expect(page).to have_link("Delete this scheme", href: "/schemes/#{scheme.id}/delete-confirmation") end end end end describe "#details" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/details" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/details" end it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, confirmed: nil) } let(:another_scheme) { create(:scheme, confirmed: nil) } before do sign_in user get "/schemes/#{scheme.id}/details" end it "returns a template for a support" do expect(response).to have_http_status(:ok) expect(page).to have_content("Create a new supported housing scheme") end context "when attempting to access check-answers scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/details" end it "returns 401" do expect(response).to be_unauthorized end end context "and the scheme is confirmed" do before do scheme.update!(confirmed: true) get "/schemes/#{scheme.id}/details" end it "redirects to a view scheme page" do follow_redirect! expect(response).to have_http_status(:ok) expect(path).to match("/schemes/#{scheme.id}") expect(page).to have_content(scheme.service_name) assert_select "a", text: /Change/, count: 3 end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme, confirmed: nil) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/details" end it "returns a template for a support" do expect(response).to have_http_status(:ok) expect(page).to have_content("Create a new supported housing scheme") end end end describe "#edit_name" do context "when not signed in" do it "redirects to the sign in page" do get "/schemes/1/edit-name" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation) } before do sign_in user get "/schemes/#{scheme.id}/edit-name" end it "returns 401" do expect(response).to be_unauthorized end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let!(:scheme) { create(:scheme, owning_organisation: user.organisation) } let!(:another_scheme) { create(:scheme) } before do sign_in user get "/schemes/#{scheme.id}/edit-name" end it "returns a template for a edit-name" do expect(response).to have_http_status(:ok) expect(page).to have_content("Scheme details") expect(page).to have_content("This scheme contains confidential information") end context "when there are stock owners" do let(:parent_organisation) { create(:organisation) } before do create(:organisation_relationship, parent_organisation:, child_organisation: user.organisation) get "/schemes/#{scheme.id}/edit-name" end it "includes the owning organisation question" do expect(response).to have_http_status(:ok) expect(page).to have_content("Which organisation owns the housing stock for this scheme?") end end context "when there are no stock owners" do before do get "/schemes/#{scheme.id}/edit-name" end context "and there are no absorbed organisations" do it "does not include the owning organisation question" do expect(response).to have_http_status(:ok) expect(page).not_to have_content("Which organisation owns the housing stock for this scheme?") end end context "and there are organisations absorbed during an open collection period" do let(:merged_organisation) { create(:organisation) } before do merged_organisation.update!(absorbing_organisation: user.organisation, merge_date: Time.zone.today) get "/schemes/#{scheme.id}/edit-name" end it "includes the owning organisation question" do expect(response).to have_http_status(:ok) expect(page).to have_content("Which organisation owns the housing stock for this scheme?") end end context "and there are no recently absorbed organisations" do let(:merged_organisation) { create(:organisation) } before do merged_organisation.update!(absorbing_organisation: user.organisation, merge_date: Time.zone.today - 2.years) get "/schemes/#{scheme.id}/edit-name" end it "does not include the owning organisation question" do expect(response).to have_http_status(:ok) expect(page).not_to have_content("Which organisation owns the housing stock for this scheme?") end end end context "when attempting to access secondary-client-group scheme page for another organisation" do before do get "/schemes/#{another_scheme.id}/edit-name" end it "returns 401" do expect(response).to be_unauthorized end end end context "when signed in as a support user" do let(:user) { create(:user, :support) } let!(:scheme) { create(:scheme) } before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/edit-name" end it "returns a template for a secondary-client-group" do expect(response).to have_http_status(:ok) expect(page).to have_content("Scheme details") expect(page).to have_content("This scheme contains confidential information") expect(page).to have_content("Which organisation owns the housing stock for this scheme?") end end end describe "#deactivate" do context "when not signed in" do it "redirects to the sign in page" do patch "/schemes/1/new-deactivation" expect(response).to redirect_to("/account/sign-in") end end context "when signed in as a data provider" do let(:user) { create(:user) } let(:scheme) { create(:scheme, owning_organisation: user.organisation, created_at: Time.zone.today) } before do sign_in user patch "/schemes/#{scheme.id}/new-deactivation" end it "returns 401" do expect(response).to be_unauthorized end end context "when signed in as a data coordinator" do let(:user) { create(:user, :data_coordinator) } let!(:scheme) { create(:scheme, owning_organisation: user.organisation, created_at: Time.zone.local(2023, 10, 11)) } let!(:location) { create(:location, scheme:) } let(:deactivation_date) { Time.utc(2022, 10, 10) } let(:lettings_log) { create(:lettings_log, :sh, location:, scheme:, startdate:, owning_organisation: user.organisation, assigned_to: user) } let(:startdate) { Time.utc(2022, 10, 11) } let(:setup_schemes) { nil } before do allow(FormHandler.instance).to receive(:lettings_in_crossover_period?).and_return(true) Timecop.freeze(Time.utc(2023, 10, 10)) Singleton.__init__(FormHandler) lettings_log sign_in user setup_schemes patch "/schemes/#{scheme.id}/new-deactivation", params: end after do Timecop.unfreeze Singleton.__init__(FormHandler) end context "with default date" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "default", deactivation_date: } } } context "and affected logs" do it "redirects to the confirmation page" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("This change will affect #{scheme.lettings_logs.count} log and 1 location.") end end context "and no affected logs" do let(:setup_schemes) { scheme.lettings_logs.update(scheme: nil) } before do create(:location_deactivation_period, deactivation_date: Time.zone.local(2022, 4, 1), reactivation_date: nil, location:) end it "redirects to the scheme page and updates the deactivation period" do follow_redirect! follow_redirect! follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_css(".govuk-notification-banner.govuk-notification-banner--success") scheme.reload expect(scheme.scheme_deactivation_periods.count).to eq(1) expect(scheme.scheme_deactivation_periods.first.deactivation_date).to eq(Time.zone.local(2022, 4, 1)) end end end context "with other date" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "10", "deactivation_date(2i)": "10", "deactivation_date(1i)": "2022" } } } context "and affected logs" do it "redirects to the confirmation page" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("This change will affect #{scheme.lettings_logs.count} log and 1 location.") end end context "and no affected logs" do let(:setup_schemes) { scheme.lettings_logs.update(scheme: nil) } before do create(:location_deactivation_period, deactivation_date: Time.zone.local(2022, 4, 5), reactivation_date: nil, location:) end it "redirects to the scheme page and updates the deactivation period" do follow_redirect! follow_redirect! follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_css(".govuk-notification-banner.govuk-notification-banner--success") scheme.reload expect(scheme.scheme_deactivation_periods.count).to eq(1) expect(scheme.scheme_deactivation_periods.first.deactivation_date).to eq(Time.zone.local(2022, 10, 10)) end end end context "when confirming deactivation" do let(:params) { { deactivation_date:, confirm: true, deactivation_date_type: "other" } } before do Timecop.freeze(Time.utc(2022, 10, 10)) sign_in user end after do Timecop.unfreeze end context "and a log startdate is after scheme deactivation date" do before do allow(LocationOrSchemeDeactivationMailer).to receive(:send_deactivation_mail).and_call_original patch "/schemes/#{scheme.id}/deactivate", params: end it "updates existing scheme with valid deactivation date and renders scheme page" do follow_redirect! follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_css(".govuk-notification-banner.govuk-notification-banner--success") scheme.reload expect(scheme.scheme_deactivation_periods.count).to eq(1) expect(scheme.scheme_deactivation_periods.first.deactivation_date).to eq(deactivation_date) end it "clears the scheme and scheme answers" do expect(lettings_log.scheme).to eq(scheme) expect(lettings_log.scheme).to eq(scheme) lettings_log.reload expect(lettings_log.scheme).to eq(nil) expect(lettings_log.scheme).to eq(nil) end it "marks log as needing attention" do expect(lettings_log.unresolved).to eq(nil) lettings_log.reload expect(lettings_log.unresolved).to eq(true) end it "sends deactivation emails" do expect(LocationOrSchemeDeactivationMailer).to have_received(:send_deactivation_mail).with( user, 1, update_logs_lettings_logs_url, scheme.service_name, ) end end context "and a log startdate is before scheme deactivation date" do let(:startdate) { Time.utc(2022, 10, 9) } it "does not update the log" do expect(lettings_log.scheme).to eq(scheme) expect(lettings_log.scheme).to eq(scheme) lettings_log.reload expect(lettings_log.scheme).to eq(scheme) expect(lettings_log.scheme).to eq(scheme) end it "does not mark log as needing attention" do expect(lettings_log.unresolved).to eq(nil) lettings_log.reload expect(lettings_log.unresolved).to eq(nil) end end context "and there already is a deactivation period" do let(:add_deactivations) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 6, 5), reactivation_date: nil, scheme:) } before do create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 6, 5), reactivation_date: nil, scheme:) patch "/schemes/#{scheme.id}/deactivate", params: end it "updates existing scheme with valid deactivation date and renders scheme page" do follow_redirect! follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_css(".govuk-notification-banner.govuk-notification-banner--success") scheme.reload expect(scheme.scheme_deactivation_periods.count).to eq(1) expect(scheme.scheme_deactivation_periods.first.deactivation_date).to eq(deactivation_date) end it "clears the scheme and scheme answers" do expect(lettings_log.scheme).to eq(scheme) lettings_log.reload expect(lettings_log.scheme).to eq(nil) expect(lettings_log.scheme).to eq(nil) end it "marks log as needing attention" do expect(lettings_log.unresolved).to eq(nil) lettings_log.reload expect(lettings_log.unresolved).to eq(true) end end context "and the users need to be notified" do it "sends E-mails to the creators of affected logs with counts" do expect { patch "/schemes/#{scheme.id}/deactivate", params: }.to enqueue_job(ActionMailer::MailDeliveryJob) end end end context "when the date is not selected" do let(:params) { { scheme_deactivation_period: { "deactivation_date": "" } } } it "displays the new page with an error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("validations.scheme.toggle_date.not_selected")) end end context "when invalid date is entered" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "10", "deactivation_date(2i)": "44", "deactivation_date(1i)": "2022" } } } it "displays the new page with an error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("validations.scheme.toggle_date.invalid")) end end context "when the date is entered is before the beginning of current collection window" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "10", "deactivation_date(2i)": "4", "deactivation_date(1i)": "2020" } } } it "displays the new page with an error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("validations.scheme.toggle_date.out_of_range", date: "1 April 2022")) end end context "when the day is not entered" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "", "deactivation_date(2i)": "2", "deactivation_date(1i)": "2022" } } } it "displays page with an error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("validations.scheme.toggle_date.invalid")) end end context "when the month is not entered" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "2", "deactivation_date(2i)": "", "deactivation_date(1i)": "2022" } } } it "displays page with an error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("validations.scheme.toggle_date.invalid")) end end context "when the year is not entered" do let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "2", "deactivation_date(2i)": "2", "deactivation_date(1i)": "" } } } it "displays page with an error message" do expect(response).to have_http_status(:unprocessable_entity) expect(page).to have_content(I18n.t("validations.scheme.toggle_date.invalid")) end end context "when there is an earlier open deactivation" do let(:deactivation_date) { Time.zone.local(2022, 10, 10) } let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "8", "deactivation_date(2i)": "9", "deactivation_date(1i)": "2023" } } } let(:add_deactivations) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 6, 5), reactivation_date: nil, scheme:) } before do create(:location_deactivation_period, deactivation_date: Time.zone.local(2022, 4, 5), reactivation_date: nil, location:) end it "redirects to the scheme page and updates the existing deactivation period" do follow_redirect! follow_redirect! follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_css(".govuk-notification-banner.govuk-notification-banner--success") scheme.reload expect(scheme.scheme_deactivation_periods.count).to eq(1) expect(scheme.scheme_deactivation_periods.first.deactivation_date).to eq(Time.zone.local(2023, 9, 8)) end end context "when there is a later open deactivation" do let(:deactivation_date) { Time.zone.local(2022, 10, 10) } let(:params) { { scheme_deactivation_period: { deactivation_date_type: "other", "deactivation_date(3i)": "8", "deactivation_date(2i)": "9", "deactivation_date(1i)": "2022" } } } let(:add_deactivations) { create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2023, 6, 5), reactivation_date: nil, scheme:) } it "redirects to the confirmation page" do follow_redirect! expect(response).to have_http_status(:ok) expect(page).to have_content("This change will affect 1 log and 1 location.") end end end end describe "#delete-confirmation" do let(:scheme) { create(:scheme, owning_organisation: user.organisation) } before do Timecop.freeze(Time.utc(2022, 10, 10)) scheme.scheme_deactivation_periods << create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 9), scheme:) scheme.save! get "/schemes/#{scheme.id}/delete-confirmation" end after do Timecop.unfreeze end context "when not signed in" do it "redirects to the sign in page" do expect(response).to redirect_to("/account/sign-in") end end context "when signed in" do before do allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user get "/schemes/#{scheme.id}/delete-confirmation" end context "with a data provider user" do let(:user) { create(:user) } it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "with a data coordinator user" do let(:user) { create(:user, :data_coordinator) } it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "with a support user user" do let(:user) { create(:user, :support) } it "shows the correct title" do expect(page.find("h1").text).to include "Are you sure you want to delete this scheme?" end it "shows a warning to the user" do expect(page).to have_selector(".govuk-warning-text", text: "You will not be able to undo this action") end it "shows a button to delete the selected scheme" do expect(page).to have_selector("form.button_to button", text: "Delete this scheme") end it "the delete scheme button submits the correct data to the correct path" do form_containing_button = page.find("form.button_to") expect(form_containing_button[:action]).to eq scheme_delete_path(scheme) expect(form_containing_button).to have_field "_method", type: :hidden, with: "delete" end it "shows a cancel link with the correct style" do expect(page).to have_selector("a.govuk-button--secondary", text: "Cancel") end it "shows cancel link that links back to the scheme page" do expect(page).to have_link(text: "Cancel", href: scheme_path(scheme)) end end end end describe "#delete" do let(:scheme) { create(:scheme, service_name: "Scheme to delete", owning_organisation: user.organisation) } let!(:locations) { create_list(:location, 2, scheme:, created_at: Time.zone.local(2022, 4, 1)) } before do delete "/schemes/#{scheme.id}/delete" end context "when not signed in" do it "redirects to the sign in page" do expect(response).to redirect_to("/account/sign-in") end end context "when signed in" do before do Timecop.freeze(Time.utc(2022, 10, 10)) scheme.scheme_deactivation_periods << create(:scheme_deactivation_period, deactivation_date: Time.zone.local(2022, 10, 9), scheme:) scheme.save! allow(user).to receive(:need_two_factor_authentication?).and_return(false) sign_in user delete "/schemes/#{scheme.id}/delete" end after do Timecop.unfreeze end context "with a data provider user" do let(:user) { create(:user) } it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "with a data coordinator user" do let(:user) { create(:user, :data_coordinator) } it "returns 401 unauthorized" do expect(response).to have_http_status(:unauthorized) end end context "with a support user user" do let(:user) { create(:user, :support) } it "deletes the scheme" do scheme.reload expect(scheme.status).to eq(:deleted) expect(scheme.discarded_at).not_to be nil end it "deletes associated locations" do locations.each do |location| location.reload expect(location.status).to eq(:deleted) expect(location.discarded_at).not_to be nil end end it "redirects to the schemes list and displays a notice that the scheme has been deleted" do expect(response).to redirect_to schemes_organisation_path(scheme.owning_organisation) follow_redirect! expect(page).to have_selector(".govuk-notification-banner--success") expect(page).to have_selector(".govuk-notification-banner--success", text: "Scheme to delete has been deleted.") end it "does not display the deleted scheme" do expect(response).to redirect_to schemes_organisation_path(scheme.owning_organisation) follow_redirect! expect(page).not_to have_link("Scheme to delete") end end end end end