diff --git a/app/controllers/organisation_relationships_controller.rb b/app/controllers/organisation_relationships_controller.rb index 65617baac..0ac66bd31 100644 --- a/app/controllers/organisation_relationships_controller.rb +++ b/app/controllers/organisation_relationships_controller.rb @@ -33,14 +33,17 @@ class OrganisationRelationshipsController < ApplicationController def add_stock_owner @organisation_relationship = organisation.parent_organisation_relationships.new + authorize @organisation_relationship end def add_managing_agent @organisation_relationship = organisation.child_organisation_relationships.new + authorize @organisation_relationship end def create_stock_owner @organisation_relationship = organisation.parent_organisation_relationships.new(organisation_relationship_params) + authorize @organisation_relationship if @organisation_relationship.save(context: :stock_owner) flash[:notice] = "#{@organisation_relationship.parent_organisation.name} is now one of #{current_user.data_coordinator? ? 'your' : "this organisation's"} stock owners" redirect_to stock_owners_organisation_path @@ -52,6 +55,7 @@ class OrganisationRelationshipsController < ApplicationController def create_managing_agent @organisation_relationship = organisation.child_organisation_relationships.new(organisation_relationship_params) + authorize @organisation_relationship if @organisation_relationship.save flash[:notice] = "#{@organisation_relationship.child_organisation.name} is now one of #{current_user.data_coordinator? ? 'your' : "this organisation's"} managing agents" redirect_to managing_agents_organisation_path @@ -61,7 +65,13 @@ class OrganisationRelationshipsController < ApplicationController end end - def remove_stock_owner; end + def remove_stock_owner + organisation_relationship = OrganisationRelationship.find_by!( + parent_organisation: @target_organisation, + child_organisation: organisation, + ) + authorize organisation_relationship + end def delete_stock_owner OrganisationRelationship.find_by!( @@ -72,7 +82,13 @@ class OrganisationRelationshipsController < ApplicationController redirect_to stock_owners_organisation_path end - def remove_managing_agent; end + def remove_managing_agent + organisation_relationship = OrganisationRelationship.find_by!( + parent_organisation: organisation, + child_organisation: @target_organisation, + ) + authorize organisation_relationship + end def delete_managing_agent OrganisationRelationship.find_by!( diff --git a/app/policies/organisation_relationship_policy.rb b/app/policies/organisation_relationship_policy.rb new file mode 100644 index 000000000..4b748f597 --- /dev/null +++ b/app/policies/organisation_relationship_policy.rb @@ -0,0 +1,21 @@ +class OrganisationRelationshipPolicy + attr_reader :user, :organisation_relationship + + def initialize(user, organisation_relationship) + @user = user + @organisation_relationship = organisation_relationship + end + + %w[ + add_stock_owner? + create_stock_owner? + remove_stock_owner? + add_managing_agent? + create_managing_agent? + remove_managing_agent? + ].each do |method_name| + define_method method_name do + !user.data_provider? + end + end +end diff --git a/spec/requests/organisation_relationships_controller_spec.rb b/spec/requests/organisation_relationships_controller_spec.rb index 83af2b981..78b894b7f 100644 --- a/spec/requests/organisation_relationships_controller_spec.rb +++ b/spec/requests/organisation_relationships_controller_spec.rb @@ -296,6 +296,94 @@ RSpec.describe OrganisationRelationshipsController, type: :request do end end + context "when directly accessing the page to add a stock owner" do + let(:request) { get "/organisations/#{organisation.id}/stock-owners/add" } + + it "returns 401" do + request + expect(response).to have_http_status(:unauthorized) + end + end + + context "when directly adding a stock owner" do + let!(:stock_owner) { FactoryBot.create(:organisation) } + let(:params) do + { + "organisation_relationship": { + "parent_organisation_id": stock_owner.id, + }, + } + end + let(:request) { post "/organisations/#{organisation.id}/stock-owners", params: } + + it "returns 401" do + request + expect(response).to have_http_status(:unauthorized) + end + + it "does not create a new organisation relationship" do + expect { request }.not_to change(OrganisationRelationship, :count) + end + end + + context "when directly removing a stock owner" do + let(:stock_owner) { FactoryBot.create(:organisation) } + let(:request) { get "/organisations/#{organisation.id}/stock-owners/remove?target_organisation_id=#{stock_owner.id}" } + + before do + FactoryBot.create(:organisation_relationship, parent_organisation: stock_owner, child_organisation: organisation) + end + + it "returns 401" do + request + expect(response).to have_http_status(:unauthorized) + end + end + + context "when directly accessing the page to add a managing agent" do + let(:request) { get "/organisations/#{organisation.id}/managing-agents/add" } + + it "returns 401" do + request + expect(response).to have_http_status(:unauthorized) + end + end + + context "when directly adding a managing agent" do + let!(:managing_agent) { FactoryBot.create(:organisation) } + let(:params) do + { + "organisation_relationship": { + "child_organisation_id": managing_agent.id, + }, + } + end + let(:request) { post "/organisations/#{organisation.id}/managing-agents", params: } + + it "returns 401" do + request + expect(response).to have_http_status(:unauthorized) + end + + it "does not create a new organisation relationship" do + expect { request }.not_to change(OrganisationRelationship, :count) + end + end + + context "when directly removing a managing agent" do + let(:managing_agent) { FactoryBot.create(:organisation) } + let(:request) { get "/organisations/#{organisation.id}/managing-agents/remove?target_organisation_id=#{managing_agent.id}" } + + before do + FactoryBot.create(:organisation_relationship, parent_organisation: organisation, child_organisation: managing_agent) + end + + it "returns 401" do + request + expect(response).to have_http_status(:unauthorized) + end + end + context "when accessing the managing agents tab" do context "with an organisation that the user belongs to" do let!(:managing_agent) { FactoryBot.create(:organisation) } @@ -333,16 +421,6 @@ RSpec.describe OrganisationRelationshipsController, type: :request do end end - context "when adding a managing agent" do - before do - get "/organisations/#{organisation.id}/managing-agents/add", headers:, params: {} - end - - it "has the correct header" do - expect(response.body).to include("What is the name of your managing agent?") - end - end - context "with an organisation that are not in scope for the user, i.e. that they do not belong to" do before do get "/organisations/#{unauthorised_organisation.id}/managing-agents", headers:, params: {}