Skip to content

Commit

Permalink
Merge pull request #3078 from DFE-Digital/fe-provider-journey-claim-c…
Browse files Browse the repository at this point in the history
…ontroller-approach

FE provider journey
  • Loading branch information
rjlynch authored Aug 28, 2024
2 parents 4a8b6e1 + c2819f8 commit 3239f34
Show file tree
Hide file tree
Showing 47 changed files with 2,141 additions and 33 deletions.
1 change: 1 addition & 0 deletions app/controllers/claims_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ class ClaimsController < BasePublicController
before_action :persist_claim, only: [:new, :create]
before_action :handle_magic_link, only: [:new], if: -> { journey.start_with_magic_link? }

include AuthorisedSlugs
include FormSubmittable
include ClaimsFormCallbacks

Expand Down
29 changes: 29 additions & 0 deletions app/controllers/concerns/authorised_slugs.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
module AuthorisedSlugs
extend ActiveSupport::Concern

included do
before_action :authorise_slug!
end

def authorise_slug!
if page_sequence.requires_authorisation?(current_slug) && !authorised?
redirect_to(
page_sequence.unauthorised_path(
current_slug,
authorisation.failure_reason
)
)
end
end

def authorised?
authorisation.failure_reason.nil?
end

def authorisation
journey::Authorisation.new(
answers: journey_session.answers,
slug: current_slug
)
end
end
57 changes: 42 additions & 15 deletions app/controllers/omniauth_callbacks_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,21 +6,14 @@ class OmniauthCallbacksController < ApplicationController
def callback
auth = request.env["omniauth.auth"]

# Only keep the attributes permitted by the form
teacher_id_user_info_attributes = auth.extra.raw_info.to_h.slice(
*SignInOrContinueForm::TeacherIdUserInfoForm::DFE_IDENTITY_ATTRIBUTES.map(&:to_s)
)

redirect_to(
claim_path(
journey: current_journey_routing_name,
slug: "sign-in-or-continue",
claim: {
logged_in_with_tid: true,
teacher_id_user_info_attributes: teacher_id_user_info_attributes
}
)
)
case params[:journey]
when "further-education-payments-provider"
further_education_payments_provider_callback(auth)
else
# The callback route for student loans and additional payments isn't
# namespaced under a journey
additional_payments_callback(auth)
end
end

def failure
Expand Down Expand Up @@ -128,4 +121,38 @@ def omniauth_hash
request.env["omniauth.auth"]
end
end

def further_education_payments_provider_callback(auth)
Journeys::FurtherEducationPayments::Provider::OmniauthCallbackForm.new(
journey_session: journey_session,
auth: auth
).save!

session[:slugs] << "sign-in"

redirect_to(
claim_path(
journey: current_journey_routing_name,
slug: "verify-claim"
)
)
end

def additional_payments_callback(auth)
# Only keep the attributes permitted by the form
teacher_id_user_info_attributes = auth.extra.raw_info.to_h.slice(
*SignInOrContinueForm::TeacherIdUserInfoForm::DFE_IDENTITY_ATTRIBUTES.map(&:to_s)
)

redirect_to(
claim_path(
journey: current_journey_routing_name,
slug: "sign-in-or-continue",
claim: {
logged_in_with_tid: true,
teacher_id_user_info_attributes: teacher_id_user_info_attributes
}
)
)
end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Required to get page sequence to think this is a "normal" journey
module Journeys
module FurtherEducationPayments
module Provider
class ClaimSubmissionForm
def initialize(journey_session)
@journey_session = journey_session
end

# We don't want page sequence to redirect us
def valid?
false
end
end
end
end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
module Journeys
module FurtherEducationPayments
module Provider
class OmniauthCallbackForm
def initialize(journey_session:, auth:)
@journey_session = journey_session
@auth = auth
end

def save!
journey_session.answers.assign_attributes(
dfe_sign_in_uid: dfe_sign_in_uid,
dfe_sign_in_organisation_id: dfe_sign_in_organisation_id,
dfe_sign_in_organisation_ukprn: dfe_sign_in_organisation_ukprn,
dfe_sign_in_service_access: dfe_sign_in_service_access?,
dfe_sign_in_role_codes: dfe_sign_in_role_codes,
dfe_sign_in_first_name: dfe_sign_in_first_name,
dfe_sign_in_last_name: dfe_sign_in_last_name,
dfe_sign_in_email: dfe_sign_in_email
)

journey_session.save!
end

private

attr_reader :journey_session, :auth

def dfe_sign_in_uid
auth["uid"]
end

def dfe_sign_in_organisation_ukprn
auth.dig("extra", "raw_info", "organisation", "ukprn")
end

def dfe_sign_in_organisation_id
auth.dig("extra", "raw_info", "organisation", "id")
end

def dfe_sign_in_service_access?
dfe_sign_in_user.service_access?
end

def dfe_sign_in_user
@dfe_sign_in_user ||= DfeSignIn::Api::User.new(
organisation_id: dfe_sign_in_organisation_id,
user_id: dfe_sign_in_uid
)
end

def dfe_sign_in_role_codes
return [] unless dfe_sign_in_service_access?

dfe_sign_in_user.role_codes
end

def dfe_sign_in_first_name
auth.dig("info", "first_name")
end

def dfe_sign_in_last_name
auth.dig("info", "last_name")
end

def dfe_sign_in_email
auth.dig("info", "email")
end
end
end
end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
module Journeys
module FurtherEducationPayments
module Provider
class SessionForm < Journeys::SessionForm
attribute :claim_id, :string
end
end
end
end
Original file line number Diff line number Diff line change
@@ -0,0 +1,156 @@
module Journeys
module FurtherEducationPayments
module Provider
class VerifyClaimForm < Form
include CoursesHelper

ASSERTIONS = {
fixed_contract: %i[
contract_type
teaching_responsibilities
further_education_teaching_start_year
teaching_hours_per_week
hours_teaching_eligible_subjects
subjects_taught
],
variable_contract: %i[
contract_type
teaching_responsibilities
further_education_teaching_start_year
taught_at_least_one_term
teaching_hours_per_week
hours_teaching_eligible_subjects
subjects_taught
teaching_hours_per_week_next_term
]
}

attribute :assertions_attributes

attribute :declaration, :boolean

validates :declaration, acceptance: true

validate :all_assertions_answered

validate :claim_not_already_verified

delegate :claim, to: :answers

def claim_reference
claim.reference
end

def claimant_name
claim.full_name
end

def claimant_date_of_birth
claim.date_of_birth.strftime("%-d %B %Y")
end

def claimant_trn
claim.eligibility.teacher_reference_number
end

def claim_date
claim.created_at.to_date.strftime("%-d %B %Y")
end

def course_descriptions
@course_descriptions ||= claim.eligibility.courses_taught.map(&:description)
end

def assertions
@assertions ||= ASSERTIONS.fetch(contract_type).map do |assertion_name|
AssertionForm.new(name: assertion_name)
end
end

def assertions_attributes=(params)
(params || {}).each do |_, assertion_params|
assertions
.detect { |a| a.name == assertion_params[:name] }
&.assign_attributes(assertion_params)
end
end

def save
return false unless valid?

claim.eligibility.update!(
verification: {
assertions: assertions.map(&:attributes),
verifier: {
dfe_sign_in_uid: answers.dfe_sign_in_uid,
first_name: answers.dfe_sign_in_first_name,
last_name: answers.dfe_sign_in_last_name,
email: answers.dfe_sign_in_email
},
created_at: DateTime.now
}
)

claim.save!

true
end

def contract_type
if claim.eligibility.fixed_contract?
:fixed_contract
else
:variable_contract
end
end

private

def permitted_attributes
super + [assertions_attributes: AssertionForm.attribute_names]
end

# Make sure the errors in the summary link to the correct nested field
def all_assertions_answered
assertions.each(&:validate).each_with_index do |assertion, i|
assertion.errors.each do |error|
errors.add(
"assertions_attributes[#{i}][#{error.attribute}]",
error.full_message
)
end
end
end

def claim_not_already_verified
if claim.eligibility.verified?
errors.add(:base, "Claim has already been verified")
end
end

class AssertionForm
include ActiveModel::Model
include ActiveModel::Attributes

attribute :name, :string
attribute :outcome, :boolean

validates :name, presence: true
validates :outcome, inclusion: {
in: [true, false],
message: "Select an option"
}

def radio_options
[
RadioOption.new(id: true, name: "Yes"),
RadioOption.new(id: false, name: "No")
]
end

class RadioOption < Struct.new(:id, :name, keyword_init: true); end
end
end
end
end
end
1 change: 1 addition & 0 deletions app/models/journeys.rb
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ def self.table_name_prefix
TeacherStudentLoanReimbursement,
GetATeacherRelocationPayment,
FurtherEducationPayments,
FurtherEducationPayments::Provider,
EarlyYearsPayment::Provider::Start,
EarlyYearsPayment::Provider::Authenticated
].freeze
Expand Down
Loading

0 comments on commit 3239f34

Please sign in to comment.