From 7707db7858e3794b10142cb8d112368c7b7218d2 Mon Sep 17 00:00:00 2001 From: Kat Date: Wed, 14 Aug 2024 08:17:34 +0100 Subject: [PATCH] Calculate merge request status --- app/models/merge_request.rb | 27 +++++++++++ .../{merge_requests.rb => merge_request.rb} | 0 spec/factories/merge_request_organisation.rb | 6 +++ spec/models/merge_request_spec.rb | 47 +++++++++++++++++++ 4 files changed, 80 insertions(+) rename spec/factories/{merge_requests.rb => merge_request.rb} (100%) create mode 100644 spec/factories/merge_request_organisation.rb diff --git a/app/models/merge_request.rb b/app/models/merge_request.rb index 7c95e199c..82f7589ec 100644 --- a/app/models/merge_request.rb +++ b/app/models/merge_request.rb @@ -4,6 +4,7 @@ class MergeRequest < ApplicationRecord belongs_to :absorbing_organisation, class_name: "Organisation", optional: true has_many :merging_organisations, through: :merge_request_organisations, source: :merging_organisation belongs_to :requester, class_name: "User", optional: true + before_save :update_status! STATUS = { "merge_issues" => 0, @@ -11,6 +12,7 @@ class MergeRequest < ApplicationRecord "ready_to_merge" => 2, "processing" => 3, "request_merged" => 4, + "deleted" => 5, }.freeze enum status: STATUS @@ -21,6 +23,8 @@ class MergeRequest < ApplicationRecord merged.where("merge_requests.merge_date >= ?", open_collection_period_start_date).or(not_merged).where(discarded_at: nil) } + attr_accessor :skip_update_status + def absorbing_organisation_name absorbing_organisation&.name || "" end @@ -32,4 +36,27 @@ class MergeRequest < ApplicationRecord def discard! update!(discarded_at: Time.zone.now) end + + def update_status! + return if skip_update_status + + self.status = calculate_status + end + + def calculate_status + return "deleted" if discarded_at.present? + return "request_merged" if status == "request_merged" + return "processing" if status == "processing" + return "incomplete" unless required_questions_answered? + return "ready_to_merge" if absorbing_organisation.data_protection_confirmed? + + "merge_issues" + end + + def required_questions_answered? + absorbing_organisation_id.present? && + merge_date.present? && + merging_organisations.count.positive? && + errors.empty? + end end diff --git a/spec/factories/merge_requests.rb b/spec/factories/merge_request.rb similarity index 100% rename from spec/factories/merge_requests.rb rename to spec/factories/merge_request.rb diff --git a/spec/factories/merge_request_organisation.rb b/spec/factories/merge_request_organisation.rb new file mode 100644 index 000000000..178401fb0 --- /dev/null +++ b/spec/factories/merge_request_organisation.rb @@ -0,0 +1,6 @@ +FactoryBot.define do + factory :merge_request_organisation do + association :merging_organisation, factory: :organisation + association :merge_request, factory: :merge_request + end +end diff --git a/spec/models/merge_request_spec.rb b/spec/models/merge_request_spec.rb index cf38d5033..6ada68985 100644 --- a/spec/models/merge_request_spec.rb +++ b/spec/models/merge_request_spec.rb @@ -42,4 +42,51 @@ RSpec.describe MergeRequest, type: :model do expect(described_class.visible).not_to include(merge_request) end end + + describe "#calculate_status" do + it "returns the correct status for deleted merge request" do + merge_request = build(:merge_request, id: 1, discarded_at: Time.zone.today) + expect(merge_request.calculate_status).to eq "deleted" + end + + it "returns the correct status for a merged request" do + merge_request = build(:merge_request, id: 1, status: "request_merged") + expect(merge_request.calculate_status).to eq "request_merged" + end + + it "returns the correct status for a ready to merge request" do + merge_request = build(:merge_request, id: 1, absorbing_organisation: create(:organisation), merge_date: Time.zone.today) + create(:merge_request_organisation, merge_request:) + expect(merge_request.calculate_status).to eq "ready_to_merge" + end + + it "returns the merge issues if dsa is not signed for absorbing organisation" do + merge_request = build(:merge_request, id: 1, absorbing_organisation: create(:organisation, with_dsa: false), merge_date: Time.zone.today) + create(:merge_request_organisation, merge_request:) + expect(merge_request.calculate_status).to eq "merge_issues" + end + + it "returns the incomplete if absorbing organisation is missing" do + merge_request = build(:merge_request, id: 1, absorbing_organisation: nil, merge_date: Time.zone.today) + create(:merge_request_organisation, merge_request:) + expect(merge_request.calculate_status).to eq "incomplete" + end + + it "returns the incomplete if merge requests organisation is missing" do + merge_request = build(:merge_request, id: 1, absorbing_organisation: create(:organisation), merge_date: Time.zone.today) + expect(merge_request.calculate_status).to eq "incomplete" + end + + it "returns the incomplete if merge date is missing" do + merge_request = build(:merge_request, id: 1, absorbing_organisation: create(:organisation)) + create(:merge_request_organisation, merge_request:) + expect(merge_request.calculate_status).to eq "incomplete" + end + + it "returns processing if merge is processing" do + merge_request = build(:merge_request, id: 1, absorbing_organisation: create(:organisation), status: "processing") + create(:merge_request_organisation, merge_request:) + expect(merge_request.calculate_status).to eq "processing" + end + end end