diff --git a/app/components/candidate_interface/application_status_tag_component.html.erb b/app/components/candidate_interface/application_status_tag_component.html.erb
index 2e41a6804bd..56812839b3b 100644
--- a/app/components/candidate_interface/application_status_tag_component.html.erb
+++ b/app/components/candidate_interface/application_status_tag_component.html.erb
@@ -1,4 +1,7 @@
<%= govuk_tag(text: text, colour: colour) %>
+<% supplementary_tags do |supplementary_tag_text, supplementary_tag_colour| %>
+ <%= govuk_tag(text: supplementary_tag_text, colour: supplementary_tag_colour) %>
+<% end %>
<% if @display_info_text %>
<% if @application_choice.application_not_sent? %>
diff --git a/app/components/candidate_interface/application_status_tag_component.rb b/app/components/candidate_interface/application_status_tag_component.rb
index c04880ca3e3..e984bc65735 100644
--- a/app/components/candidate_interface/application_status_tag_component.rb
+++ b/app/components/candidate_interface/application_status_tag_component.rb
@@ -5,6 +5,7 @@ class ApplicationStatusTagComponent < ViewComponent::Base
def initialize(application_choice:, display_info_text: true)
@application_choice = application_choice
@display_info_text = display_info_text
+ @supplementary_statuses = application_choice.respond_to?(:supplementary_statuses) ? application_choice.supplementary_statuses : []
end
def text
@@ -36,8 +37,27 @@ def colour
end
end
+ def supplementary_tags
+ @supplementary_statuses.each do |supplementary_status|
+ yield supplementary_tag_text(supplementary_status), supplementary_tag_colour(supplementary_status)
+ end
+ end
+
private
+ def supplementary_tag_text(supplementary_status)
+ I18n.t!("supplementary_application_states.#{supplementary_status}.name")
+ end
+
+ def supplementary_tag_colour(supplementary_status)
+ case supplementary_status.to_s
+ when 'ske_pending_conditions'
+ 'blue'
+ else
+ raise "You need to define a colour for the #{supplementary_status} supplementary state"
+ end
+ end
+
attr_reader :application_choice
end
end
diff --git a/app/components/candidate_interface/continuous_applications/application_review_component.rb b/app/components/candidate_interface/continuous_applications/application_review_component.rb
index e812ee77ec2..4b94cfa36ff 100644
--- a/app/components/candidate_interface/continuous_applications/application_review_component.rb
+++ b/app/components/candidate_interface/continuous_applications/application_review_component.rb
@@ -27,7 +27,9 @@ def status_row
{
key: 'Status',
- value: render(ApplicationStatusTagComponent.new(application_choice:, display_info_text: false)),
+ value: render(
+ ApplicationStatusTagComponent.new(application_choice:, display_info_text: false),
+ ),
}
end
diff --git a/app/components/candidate_interface/previous_applications_component.html.erb b/app/components/candidate_interface/previous_applications_component.html.erb
index 1e543c31d78..b64937873a2 100644
--- a/app/components/candidate_interface/previous_applications_component.html.erb
+++ b/app/components/candidate_interface/previous_applications_component.html.erb
@@ -22,7 +22,7 @@
<% end %>
- <%= render CandidateInterface::ApplicationStatusTagComponent.new(application_choice: application_choice) %>
+ <%= render CandidateInterface::ApplicationStatusTagComponent.new(application_choice:) %>
|
<% end %>
diff --git a/app/components/provider_interface/application_card_component.html.erb b/app/components/provider_interface/application_card_component.html.erb
index 7e7018b8e6d..2c7e7276fb6 100644
--- a/app/components/provider_interface/application_card_component.html.erb
+++ b/app/components/provider_interface/application_card_component.html.erb
@@ -6,7 +6,9 @@
<%= application_choice.id %>
- <%= render ProviderInterface::ApplicationStatusTagComponent.new(application_choice: application_choice) %>
+
+ <%= render(ProviderInterface::ApplicationStatusTagComponent.new(application_choice:)) %>
+
diff --git a/app/components/provider_interface/application_choice_header_component.html.erb b/app/components/provider_interface/application_choice_header_component.html.erb
index a279053fca6..6e91df1135a 100644
--- a/app/components/provider_interface/application_choice_header_component.html.erb
+++ b/app/components/provider_interface/application_choice_header_component.html.erb
@@ -1,6 +1,8 @@
<%= application_choice.application_form.full_name %>
- <%= render(ProviderInterface::ApplicationStatusTagComponent.new(application_choice: application_choice)) %>
+
+ <%= render(ProviderInterface::ApplicationStatusTagComponent.new(application_choice:)) %>
+
<% if show_inset_text? -%>
diff --git a/app/components/provider_interface/application_status_tag_component.html.erb b/app/components/provider_interface/application_status_tag_component.html.erb
index a32d93128a1..9d581972d8c 100644
--- a/app/components/provider_interface/application_status_tag_component.html.erb
+++ b/app/components/provider_interface/application_status_tag_component.html.erb
@@ -1 +1,4 @@
<%= govuk_tag(text: text, colour: colour) %>
+<% supplementary_tags do |supplementary_tag_text, supplementary_tag_colour| %>
+ <%= govuk_tag(text: supplementary_tag_text, colour: supplementary_tag_colour) %>
+<% end %>
diff --git a/app/components/provider_interface/application_status_tag_component.rb b/app/components/provider_interface/application_status_tag_component.rb
index c29429d9f6b..86583f38434 100644
--- a/app/components/provider_interface/application_status_tag_component.rb
+++ b/app/components/provider_interface/application_status_tag_component.rb
@@ -4,6 +4,7 @@ class ApplicationStatusTagComponent < ViewComponent::Base
def initialize(application_choice:)
@application_choice = application_choice
+ @supplementary_statuses = application_choice.respond_to?(:supplementary_statuses) ? application_choice.supplementary_statuses : []
end
def text
@@ -33,8 +34,27 @@ def colour
end
end
+ def supplementary_tags
+ @supplementary_statuses.each do |supplementary_status|
+ yield supplementary_tag_text(supplementary_status), supplementary_tag_colour(supplementary_status)
+ end
+ end
+
private
+ def supplementary_tag_text(supplementary_status)
+ I18n.t!("supplementary_application_states.#{supplementary_status}.name")
+ end
+
+ def supplementary_tag_colour(supplementary_status)
+ case supplementary_status.to_s
+ when 'ske_pending_conditions'
+ 'blue'
+ else
+ raise "You need to define a colour for the #{supplementary_status} supplementary state"
+ end
+ end
+
attr_reader :application_choice
end
end
diff --git a/app/components/support_interface/application_card_component.html.erb b/app/components/support_interface/application_card_component.html.erb
index 2302cc86685..0ec2f914fa5 100644
--- a/app/components/support_interface/application_card_component.html.erb
+++ b/app/components/support_interface/application_card_component.html.erb
@@ -11,7 +11,7 @@
<% application_choices.each do |application_choice| %>
-
- <%= render SupportInterface::ApplicationStatusTagComponent.new(status: application_choice.status) %>
+ <%= render(SupportInterface::ApplicationStatusTagComponent.new(application_choice:)) %>
<%= application_choice.current_course_option.course.name_and_code %> at <%= application_choice.current_course_option.provider.name %>
<% end %>
diff --git a/app/components/support_interface/application_choice_component.rb b/app/components/support_interface/application_choice_component.rb
index bd8b36c4446..b5d51c22563 100644
--- a/app/components/support_interface/application_choice_component.rb
+++ b/app/components/support_interface/application_choice_component.rb
@@ -41,7 +41,7 @@ def application_number_row
def status_row
{
key: 'Status',
- value: render(SupportInterface::ApplicationStatusTagComponent.new(status: application_choice.status)),
+ value: render(SupportInterface::ApplicationStatusTagComponent.new(application_choice:)),
}.merge(status_action_link)
end
diff --git a/app/components/support_interface/application_status_tag_component.html.erb b/app/components/support_interface/application_status_tag_component.html.erb
index a32d93128a1..9d581972d8c 100644
--- a/app/components/support_interface/application_status_tag_component.html.erb
+++ b/app/components/support_interface/application_status_tag_component.html.erb
@@ -1 +1,4 @@
<%= govuk_tag(text: text, colour: colour) %>
+<% supplementary_tags do |supplementary_tag_text, supplementary_tag_colour| %>
+ <%= govuk_tag(text: supplementary_tag_text, colour: supplementary_tag_colour) %>
+<% end %>
diff --git a/app/components/support_interface/application_status_tag_component.rb b/app/components/support_interface/application_status_tag_component.rb
index 3a2858b9a06..a1f80c767af 100644
--- a/app/components/support_interface/application_status_tag_component.rb
+++ b/app/components/support_interface/application_status_tag_component.rb
@@ -1,7 +1,9 @@
module SupportInterface
class ApplicationStatusTagComponent < ViewComponent::Base
- def initialize(status:)
- @status = status
+ def initialize(application_choice:)
+ @status = application_choice.status
+ @supplementary_statuses =
+ application_choice.respond_to?(:supplementary_statuses) ? application_choice.supplementary_statuses : []
end
def text
@@ -26,5 +28,26 @@ def colour
raise "You need to define a colour for the #{@status} state"
end
end
+
+ def supplementary_tags
+ @supplementary_statuses.each do |supplementary_status|
+ yield supplementary_tag_text(supplementary_status), supplementary_tag_colour(supplementary_status)
+ end
+ end
+
+ private
+
+ def supplementary_tag_text(supplementary_status)
+ I18n.t!("supplementary_application_states.#{supplementary_status}.name")
+ end
+
+ def supplementary_tag_colour(supplementary_status)
+ case supplementary_status.to_s
+ when 'ske_pending_conditions'
+ 'blue'
+ else
+ raise "You need to define a colour for the #{supplementary_status} supplementary state"
+ end
+ end
end
end
diff --git a/app/models/application_choice.rb b/app/models/application_choice.rb
index 7fa90d54acf..93de4207884 100644
--- a/app/models/application_choice.rb
+++ b/app/models/application_choice.rb
@@ -257,6 +257,14 @@ def science_gcse_needed?
course.primary_course?
end
+ def supplementary_statuses
+ [].tap do |supplementary_statuses|
+ if recruited? && RecruitedWithPendingConditions.new(application_choice: self).call
+ supplementary_statuses << :ske_pending_conditions
+ end
+ end
+ end
+
private
def set_initial_status
diff --git a/app/services/can_recruit_with_pending_conditions.rb b/app/services/can_recruit_with_pending_conditions.rb
index 38b43dde8fb..4704ab7194f 100644
--- a/app/services/can_recruit_with_pending_conditions.rb
+++ b/app/services/can_recruit_with_pending_conditions.rb
@@ -1,38 +1,13 @@
-class CanRecruitWithPendingConditions
- attr_accessor :application_choice
-
- def initialize(application_choice:)
- self.application_choice = application_choice
- end
-
+class CanRecruitWithPendingConditions < HasPendingSkeConditionsOnly
def call
- feature_flag_enabled? &&
- application_has_offer? &&
- offer_has_pending_ske_conditions? &&
- all_non_ske_conditions_met? &&
+ application_choice.pending_conditions? &&
+ pending_ske_conditions_only? &&
provider_is_scitt? &&
course_is_within_time_limit?
end
private
- def feature_flag_enabled?
- FeatureFlag.active?(:recruit_with_pending_conditions)
- end
-
- def application_has_offer?
- application_choice.offer.present?
- end
-
- def offer_has_pending_ske_conditions?
- application_choice.offer.ske_conditions.any?(&:pending?)
- end
-
- def all_non_ske_conditions_met?
- non_ske_conditions = application_choice.offer.conditions - application_choice.offer.ske_conditions
- non_ske_conditions.all?(&:met?)
- end
-
def provider_is_scitt?
application_choice.provider&.scitt?
end
diff --git a/app/services/has_pending_ske_conditions_only.rb b/app/services/has_pending_ske_conditions_only.rb
new file mode 100644
index 00000000000..7e248faddb3
--- /dev/null
+++ b/app/services/has_pending_ske_conditions_only.rb
@@ -0,0 +1,35 @@
+class HasPendingSkeConditionsOnly
+ attr_accessor :application_choice
+
+ def initialize(application_choice:)
+ self.application_choice = application_choice
+ end
+
+ def pending_ske_conditions_only?
+ feature_flag_enabled? &&
+ application_has_offer? &&
+ offer_has_pending_ske_conditions? &&
+ all_non_ske_conditions_met?
+ end
+
+private
+
+ def feature_flag_enabled?
+ FeatureFlag.active?(:recruit_with_pending_conditions)
+ end
+
+ def application_has_offer?
+ application_choice.offer.present?
+ end
+
+ def offer_has_pending_ske_conditions?
+ application_choice.offer.conditions.any? do |condition|
+ condition.is_a?(SkeCondition) && condition.pending?
+ end
+ end
+
+ def all_non_ske_conditions_met?
+ non_ske_conditions = application_choice.offer.conditions - application_choice.offer.ske_conditions
+ non_ske_conditions.all?(&:met?)
+ end
+end
diff --git a/app/services/recruited_with_pending_conditions.rb b/app/services/recruited_with_pending_conditions.rb
new file mode 100644
index 00000000000..402ace57c00
--- /dev/null
+++ b/app/services/recruited_with_pending_conditions.rb
@@ -0,0 +1,5 @@
+class RecruitedWithPendingConditions < HasPendingSkeConditionsOnly
+ def call
+ application_choice.recruited? && pending_ske_conditions_only?
+ end
+end
diff --git a/app/views/provider_interface/offer/recruit_with_pending_conditions/new.html.erb b/app/views/provider_interface/offer/recruit_with_pending_conditions/new.html.erb
index c13b1e88680..c47d4358935 100644
--- a/app/views/provider_interface/offer/recruit_with_pending_conditions/new.html.erb
+++ b/app/views/provider_interface/offer/recruit_with_pending_conditions/new.html.erb
@@ -2,7 +2,11 @@
<%= @application_choice.application_form.full_name %>
- <%= render(ProviderInterface::ApplicationStatusTagComponent.new(application_choice: @application_choice)) %>
+ <%= render(
+ ProviderInterface::ApplicationStatusTagComponent.new(
+ application_choice: @application_choice,
+ ),
+ ) %>
<%= form_with(
diff --git a/config/locales/application_states.yml b/config/locales/application_states.yml
index ac821dc4084..4807c8c22c9 100644
--- a/config/locales/application_states.yml
+++ b/config/locales/application_states.yml
@@ -221,6 +221,11 @@ en:
emails:
- candidate_mailer-deferred_offer_reminder
+ supplementary_application_states:
+ ske_pending_conditions:
+ name: SKE conditions pending
+ description: Provider is waiting for the candidate to meet one or more SKE conditions.
+
events:
unsubmitted-send_to_provider:
name: Candidate submits
diff --git a/spec/components/candidate_interface/application_status_tag_component_spec.rb b/spec/components/candidate_interface/application_status_tag_component_spec.rb
index 51dbbd47d68..311ace361ec 100644
--- a/spec/components/candidate_interface/application_status_tag_component_spec.rb
+++ b/spec/components/candidate_interface/application_status_tag_component_spec.rb
@@ -224,4 +224,13 @@
end
end
end
+
+ it 'renders with `ske_pending_condition` supplementary status for `recruited` applications' do
+ application_choice = build_stubbed(:application_choice, status: :recruited)
+ allow(application_choice).to receive(:supplementary_statuses).and_return([:ske_pending_conditions])
+
+ result = render_inline described_class.new(application_choice:)
+ expect(result.text).to include('Offer confirmed')
+ expect(result.text).to include('SKE conditions pending')
+ end
end
diff --git a/spec/components/provider_interface/application_status_tag_component_spec.rb b/spec/components/provider_interface/application_status_tag_component_spec.rb
index 23643178093..30874add60f 100644
--- a/spec/components/provider_interface/application_status_tag_component_spec.rb
+++ b/spec/components/provider_interface/application_status_tag_component_spec.rb
@@ -6,4 +6,16 @@
render_inline described_class.new(application_choice: build_stubbed(:application_choice, status: state_name))
end
end
+
+ it 'renders with `ske_pending_condition` supplementary status for `recruited` applications' do
+ application_choice = build_stubbed(
+ :application_choice,
+ status: :recruited,
+ )
+ allow(application_choice).to receive(:supplementary_statuses).and_return([:ske_pending_conditions])
+
+ result = render_inline described_class.new(application_choice:)
+ expect(result.text).to include('Recruited')
+ expect(result.text).to include('SKE conditions pending')
+ end
end
diff --git a/spec/components/provider_interface/offer_summary_component_spec.rb b/spec/components/provider_interface/offer_summary_component_spec.rb
index 144fd73817d..50c4dece2c6 100644
--- a/spec/components/provider_interface/offer_summary_component_spec.rb
+++ b/spec/components/provider_interface/offer_summary_component_spec.rb
@@ -192,7 +192,7 @@ def row_link_selector(row_number)
end
end
- context 'when application is in condititions_pending state but only SKE conditions are pending' do
+ context 'when application is in conditions_pending state but only SKE conditions are pending' do
let(:application_choice) { build_stubbed(:application_choice, :accepted) }
before { allow(CanRecruitWithPendingConditions).to receive(:new).and_return(instance_double(CanRecruitWithPendingConditions, call: true)) }
diff --git a/spec/components/support_interface/application_status_tag_component_spec.rb b/spec/components/support_interface/application_status_tag_component_spec.rb
index 08f58b1a171..ac96613d773 100644
--- a/spec/components/support_interface/application_status_tag_component_spec.rb
+++ b/spec/components/support_interface/application_status_tag_component_spec.rb
@@ -3,7 +3,21 @@
RSpec.describe SupportInterface::ApplicationStatusTagComponent do
ApplicationStateChange.valid_states.each do |state_name|
it "renders with a #{state_name} application choice" do
- render_inline described_class.new(status: state_name.to_s)
+ application_choice = instance_double(ApplicationChoice, status: state_name)
+
+ render_inline described_class.new(application_choice:)
end
end
+
+ it 'renders with `ske_pending_condition` supplementary status for `recruited` applications' do
+ application_choice = instance_double(
+ ApplicationChoice,
+ status: :recruited,
+ supplementary_statuses: [:ske_pending_conditions],
+ )
+
+ result = render_inline described_class.new(application_choice:)
+ expect(result.text).to include('Recruited')
+ expect(result.text).to include('SKE conditions pending')
+ end
end
diff --git a/spec/factories/offer.rb b/spec/factories/offer.rb
index 40627de20ff..fd225fb4072 100644
--- a/spec/factories/offer.rb
+++ b/spec/factories/offer.rb
@@ -15,6 +15,8 @@
end
trait :with_ske_conditions do
+ application_choice { association(:application_choice, :pending_conditions, offer: instance) }
+
conditions {
[
build(:text_condition),
diff --git a/spec/models/application_choice_spec.rb b/spec/models/application_choice_spec.rb
index ff39bcb7a52..89169699271 100644
--- a/spec/models/application_choice_spec.rb
+++ b/spec/models/application_choice_spec.rb
@@ -530,4 +530,20 @@
end
end
end
+
+ describe '#supplementary_statuses' do
+ let(:service) { instance_double(RecruitedWithPendingConditions, call: true) }
+
+ before { allow(RecruitedWithPendingConditions).to receive(:new).and_return(service) }
+
+ it 'returns an empty array if the status is not `recruited`' do
+ application_choice = build(:application_choice, :offer)
+ expect(application_choice.supplementary_statuses).to eq([])
+ end
+
+ it 'returns `ske_pending_conditions` if the status is `recruited`' do
+ application_choice = build(:application_choice, :recruited)
+ expect(application_choice.supplementary_statuses).to eq([:ske_pending_conditions])
+ end
+ end
end
diff --git a/spec/services/can_recruit_with_pending_conditions_spec.rb b/spec/services/can_recruit_with_pending_conditions_spec.rb
index 7ee8df8c1a7..74ab69fc131 100644
--- a/spec/services/can_recruit_with_pending_conditions_spec.rb
+++ b/spec/services/can_recruit_with_pending_conditions_spec.rb
@@ -23,14 +23,6 @@
context 'when feature flag is on' do
before { FeatureFlag.activate(:recruit_with_pending_conditions) }
- context 'when there are various pending conditions' do
- let(:offer) { create(:offer, :with_unmet_conditions) }
-
- it 'returns false' do
- expect(service.call).to be(false)
- end
- end
-
context 'when there is a pending SKE condition and other met conditions' do
let(:offer) { create(:offer, :with_ske_conditions) }
@@ -48,6 +40,16 @@
end
end
+ context 'when the application choice is already `recruited`' do
+ before do
+ offer.application_choice.recruited!
+ end
+
+ it 'returns false if the status is already `recruited`' do
+ expect(service.call).to be(false)
+ end
+ end
+
context 'when the provider is NOT a SCITT and the course start date is within 3 months' do
before do
offer.application_choice.provider.update(provider_type: :university)
diff --git a/spec/services/recruited_with_pending_conditions_spec.rb b/spec/services/recruited_with_pending_conditions_spec.rb
new file mode 100644
index 00000000000..69048c5080e
--- /dev/null
+++ b/spec/services/recruited_with_pending_conditions_spec.rb
@@ -0,0 +1,44 @@
+require 'rails_helper'
+
+RSpec.describe RecruitedWithPendingConditions do
+ let(:offer) { create(:offer) }
+
+ subject(:service) { described_class.new(application_choice: offer.application_choice) }
+
+ context 'when feature flag is off' do
+ let(:offer) { create(:offer, :with_ske_conditions) }
+
+ before do
+ offer.conditions.reject { |condition| condition.is_a?(SkeCondition) }.each do |condition|
+ condition.update!(status: :met)
+ end
+ end
+
+ it 'returns false' do
+ expect(service.call).to be(false)
+ end
+ end
+
+ context 'when feature flag is on' do
+ before { FeatureFlag.activate(:recruit_with_pending_conditions) }
+
+ context 'when there is a pending SKE condition and other met conditions' do
+ let(:offer) { create(:offer, :with_ske_conditions) }
+
+ before do
+ offer.conditions.reject { |condition| condition.is_a?(SkeCondition) }.each do |condition|
+ condition.update!(status: :met)
+ end
+ end
+
+ it 'returns false if the status is `pending_conditions`' do
+ expect(service.call).to be(false)
+ end
+
+ it 'returns true if the status is `recruited`' do
+ offer.application_choice.recruited!
+ expect(service.call).to be(true)
+ end
+ end
+ end
+end