diff --git a/app/controllers/concerns/verify_profile_concern.rb b/app/controllers/concerns/verify_profile_concern.rb index d49791c025f..6345dd54f04 100644 --- a/app/controllers/concerns/verify_profile_concern.rb +++ b/app/controllers/concerns/verify_profile_concern.rb @@ -10,6 +10,8 @@ def account_or_verify_profile_url def profile_needs_verification? return false if current_user.blank? + return false if sp_session[:ial2_strict] && + !IdentityConfig.store.gpo_allowed_for_strict_ial2 current_user.decorate.pending_profile_requires_verification? || user_needs_to_reactivate_account? end diff --git a/app/controllers/idv/doc_auth_controller.rb b/app/controllers/idv/doc_auth_controller.rb index d22e70162d1..45a937fc904 100644 --- a/app/controllers/idv/doc_auth_controller.rb +++ b/app/controllers/idv/doc_auth_controller.rb @@ -31,6 +31,8 @@ def redirect_if_mail_bounced end def redirect_if_pending_profile + return if sp_session[:ial2_strict] && + !IdentityConfig.store.gpo_allowed_for_strict_ial2 redirect_to idv_gpo_verify_url if current_user.decorate.pending_profile_requires_verification? end diff --git a/app/controllers/idv/gpo_controller.rb b/app/controllers/idv/gpo_controller.rb index eb20b2b5079..c7df8e8ae70 100644 --- a/app/controllers/idv/gpo_controller.rb +++ b/app/controllers/idv/gpo_controller.rb @@ -6,6 +6,7 @@ class GpoController < ApplicationController before_action :confirm_idv_needed before_action :confirm_user_completed_idv_profile_step before_action :confirm_mail_not_spammed + before_action :confirm_gpo_allowed_if_strict_ial2 before_action :max_attempts_reached, only: [:update] def index @@ -65,6 +66,12 @@ def failure redirect_to idv_gpo_url unless performed? end + def confirm_gpo_allowed_if_strict_ial2 + return unless sp_session[:ial2_strict] + return if IdentityConfig.store.gpo_allowed_for_strict_ial2 + redirect_to idv_phone_url + end + def pii(address_pii) address_pii.dup.merge(non_address_pii) end diff --git a/app/controllers/idv/otp_delivery_method_controller.rb b/app/controllers/idv/otp_delivery_method_controller.rb index d55123e566a..108d87d1416 100644 --- a/app/controllers/idv/otp_delivery_method_controller.rb +++ b/app/controllers/idv/otp_delivery_method_controller.rb @@ -79,8 +79,11 @@ def otp_delivery_selection_form end def gpo_letter_available + return @gpo_letter_available if defined?(@gpo_letter_available) @gpo_letter_available ||= FeatureManagement.enable_gpo_verification? && - !Idv::GpoMail.new(current_user).mail_spammed? + !Idv::GpoMail.new(current_user).mail_spammed? && + !(sp_session[:ial2_strict] && + !IdentityConfig.store.gpo_allowed_for_strict_ial2) end end end diff --git a/app/controllers/idv/phone_controller.rb b/app/controllers/idv/phone_controller.rb index fdb6d6d5d83..af0e5131b00 100644 --- a/app/controllers/idv/phone_controller.rb +++ b/app/controllers/idv/phone_controller.rb @@ -140,8 +140,11 @@ def new_phone_added? end def gpo_letter_available + return @gpo_letter_available if defined?(@gpo_letter_available) @gpo_letter_available ||= FeatureManagement.enable_gpo_verification? && - !Idv::GpoMail.new(current_user).mail_spammed? + !Idv::GpoMail.new(current_user).mail_spammed? && + !(sp_session[:ial2_strict] && + !IdentityConfig.store.gpo_allowed_for_strict_ial2) end end end diff --git a/app/controllers/idv/phone_errors_controller.rb b/app/controllers/idv/phone_errors_controller.rb index cb2d87d0a73..636c5598ae0 100644 --- a/app/controllers/idv/phone_errors_controller.rb +++ b/app/controllers/idv/phone_errors_controller.rb @@ -4,6 +4,7 @@ class PhoneErrorsController < ApplicationController before_action :confirm_two_factor_authenticated before_action :confirm_idv_phone_step_needed + before_action :set_gpo_letter_available def warning @remaining_attempts = throttle.remaining_count @@ -45,5 +46,15 @@ def track_event(type:) analytics.idv_phone_error_visited(**attributes) end + + # rubocop:disable Naming/MemoizedInstanceVariableName + def set_gpo_letter_available + return @gpo_letter_available if defined?(@gpo_letter_available) + @gpo_letter_available ||= FeatureManagement.enable_gpo_verification? && + !Idv::GpoMail.new(current_user).mail_spammed? && + !(sp_session[:ial2_strict] && + !IdentityConfig.store.gpo_allowed_for_strict_ial2) + end + # rubocop:enable Naming/MemoizedInstanceVariableName end end diff --git a/app/models/profile.rb b/app/models/profile.rb index 111e6b262ef..8eddfeeed34 100644 --- a/app/models/profile.rb +++ b/app/models/profile.rb @@ -93,7 +93,7 @@ def includes_phone_check? def strict_ial2_proofed? return false unless active return false unless includes_liveness_check? - return true if IdentityConfig.store.usps_upload_allowed_for_strict_ial2 + return true if IdentityConfig.store.gpo_allowed_for_strict_ial2 includes_phone_check? end diff --git a/app/views/idv/phone_errors/_warning.html.erb b/app/views/idv/phone_errors/_warning.html.erb index ccb0822efc8..9a722d0ecef 100644 --- a/app/views/idv/phone_errors/_warning.html.erb +++ b/app/views/idv/phone_errors/_warning.html.erb @@ -19,7 +19,7 @@ locals: text: t('idv.troubleshooting.options.contact_support', app_name: APP_NAME), new_tab: true, }, - FeatureManagement.enable_gpo_verification? && { + @gpo_letter_available && { text: t('idv.troubleshooting.options.verify_by_mail'), url: idv_gpo_path, }, diff --git a/app/views/idv/phone_errors/failure.html.erb b/app/views/idv/phone_errors/failure.html.erb index bd75ad9db9c..adde1cf968d 100644 --- a/app/views/idv/phone_errors/failure.html.erb +++ b/app/views/idv/phone_errors/failure.html.erb @@ -3,7 +3,7 @@ title: t('titles.failure.phone_verification'), heading: t('idv.failure.phone.heading'), options: [ - FeatureManagement.enable_gpo_verification? && { + @gpo_letter_available && { text: t('idv.troubleshooting.options.verify_by_mail'), url: idv_gpo_path, }, diff --git a/config/application.yml.default b/config/application.yml.default index 7a9d3309f7c..910d50efc5b 100644 --- a/config/application.yml.default +++ b/config/application.yml.default @@ -245,7 +245,7 @@ usps_ipp_root_url: '' usps_ipp_request_timeout: 10 usps_ipp_sponsor_id: '' usps_ipp_username: '' -usps_upload_allowed_for_strict_ial2: true +gpo_allowed_for_strict_ial2: true voice_otp_pause_time: '0.5s' voice_otp_speech_rate: 'slow' voip_check: true diff --git a/lib/identity_config.rb b/lib/identity_config.rb index 9d2a086c74b..9a410d4695b 100644 --- a/lib/identity_config.rb +++ b/lib/identity_config.rb @@ -327,7 +327,7 @@ def self.build_store(config_map) config.add(:usps_ipp_username, type: :string) config.add(:usps_ipp_request_timeout, type: :integer) config.add(:usps_upload_enabled, type: :boolean) - config.add(:usps_upload_allowed_for_strict_ial2, type: :boolean) + config.add(:gpo_allowed_for_strict_ial2, type: :boolean) config.add(:usps_upload_sftp_directory, type: :string) config.add(:usps_upload_sftp_host, type: :string) config.add(:usps_upload_sftp_password, type: :string) diff --git a/spec/features/idv/strict_ial2/upgrade_spec.rb b/spec/features/idv/strict_ial2/upgrade_spec.rb index fff19b5612d..3848eb056a7 100644 --- a/spec/features/idv/strict_ial2/upgrade_spec.rb +++ b/spec/features/idv/strict_ial2/upgrade_spec.rb @@ -35,7 +35,7 @@ context 'strict IAL2 does not allow a phone check' do before do allow(IdentityConfig.store).to receive( - :usps_upload_allowed_for_strict_ial2, + :gpo_allowed_for_strict_ial2, ).and_return(false) end diff --git a/spec/features/idv/strict_ial2/usps_upload_disallowed_spec.rb b/spec/features/idv/strict_ial2/usps_upload_disallowed_spec.rb new file mode 100644 index 00000000000..ec9a5c7e1fb --- /dev/null +++ b/spec/features/idv/strict_ial2/usps_upload_disallowed_spec.rb @@ -0,0 +1,76 @@ +require 'rails_helper' + +feature 'Strict IAL2 with usps upload disallowed' do + include IdvHelper + include OidcAuthHelper + include IdvHelper + include IdvStepHelper + + before do + allow(IdentityConfig.store).to receive(:liveness_checking_enabled).and_return(true) + allow(IdentityConfig.store).to receive( + :gpo_allowed_for_strict_ial2, + ).and_return(false) + end + + it 'does not allow the user to select the letter flow during proofing' do + user = create(:user, :signed_up) + visit_idp_from_oidc_sp_with_ial2_strict + sign_in_user(user) + fill_in_code_with_last_phone_otp + click_submit_default + complete_idv_steps_before_phone_step + + # Link is not present on the phone page + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + + # Link is not present on the OTP delivery selection page + fill_out_phone_form_ok('7032231234') + click_idv_continue + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + + # Link is not visible on the OTP entry page + choose_idv_otp_delivery_method_sms + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + + # Link is not visible on error or warning page + visit idv_phone_errors_warning_path + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + visit idv_phone_errors_jobfail_path + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + visit idv_phone_errors_timeout_path + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + visit idv_phone_errors_failure_path + expect(page).to_not have_content(t('idv.troubleshooting.options.verify_by_mail')) + + # Visiting the GPO page redirects + visit idv_gpo_path + expect(current_path).to eq(idv_phone_path) + end + + it 'does not prompt a pending user for a mailed code' do + user = create( + :profile, + deactivation_reason: :verification_pending, + pii: { first_name: 'John', ssn: '111223333' }, + ).user + + visit_idp_from_oidc_sp_with_ial2_strict + sign_in_user(user) + fill_in_code_with_last_phone_otp + click_submit_default + + # Directed to the start of the proofing flow instead of GPO code verification + expect(current_path).to eq(idv_doc_auth_step_path(step: :welcome)) + + complete_all_doc_auth_steps + click_continue + fill_in 'Password', with: user.password + click_continue + click_acknowledge_personal_key + click_agree_and_continue + + expect(current_url).to start_with('http://localhost:7654/auth/result') + expect(user.active_profile.strict_ial2_proofed?).to be_truthy + end +end diff --git a/spec/models/profile_spec.rb b/spec/models/profile_spec.rb index edf6d5b5731..d6c3b6f82cd 100644 --- a/spec/models/profile_spec.rb +++ b/spec/models/profile_spec.rb @@ -102,7 +102,7 @@ context 'the letter flow is allowed for strict IAL2' do before do allow(IdentityConfig.store).to receive( - :usps_upload_allowed_for_strict_ial2, + :gpo_allowed_for_strict_ial2, ).and_return(true) end @@ -124,7 +124,7 @@ context 'the letter flow is not allowed for strict IAL2' do before do allow(IdentityConfig.store).to receive( - :usps_upload_allowed_for_strict_ial2, + :gpo_allowed_for_strict_ial2, ).and_return(false) end diff --git a/spec/views/idv/phone_errors/failure.html.erb_spec.rb b/spec/views/idv/phone_errors/failure.html.erb_spec.rb index e87091921dd..02ac43246e8 100644 --- a/spec/views/idv/phone_errors/failure.html.erb_spec.rb +++ b/spec/views/idv/phone_errors/failure.html.erb_spec.rb @@ -11,6 +11,7 @@ before do decorated_session = instance_double(ServiceProviderSessionDecorator, sp_name: sp_name) allow(view).to receive(:decorated_session).and_return(decorated_session) + assign(:gpo_letter_available, true) allow(IdentityConfig.store).to receive(:idv_attempt_window_in_hours).and_return(timeout_hours) @expires_at = Time.zone.now + timeout_hours.hours diff --git a/spec/views/idv/phone_errors/jobfail.html.erb_spec.rb b/spec/views/idv/phone_errors/jobfail.html.erb_spec.rb index 5a71334b921..92f1d5a77e9 100644 --- a/spec/views/idv/phone_errors/jobfail.html.erb_spec.rb +++ b/spec/views/idv/phone_errors/jobfail.html.erb_spec.rb @@ -2,14 +2,12 @@ describe 'idv/phone_errors/jobfail.html.erb' do let(:sp_name) { 'Example SP' } - let(:enable_gpo_verification) { false } + let(:gpo_letter_available) { false } before do - allow(FeatureManagement).to receive(:enable_gpo_verification?). - and_return(enable_gpo_verification) - decorated_session = instance_double(ServiceProviderSessionDecorator, sp_name: sp_name) allow(view).to receive(:decorated_session).and_return(decorated_session) + assign(:gpo_letter_available, gpo_letter_available) render end @@ -43,7 +41,7 @@ end context 'gpo verification enabled' do - let(:enable_gpo_verification) { true } + let(:gpo_letter_available) { true } it 'renders a list of troubleshooting options' do expect(rendered).to have_link( diff --git a/spec/views/idv/phone_errors/timeout.html.erb_spec.rb b/spec/views/idv/phone_errors/timeout.html.erb_spec.rb index 2f9f3135b9d..0c481b89724 100644 --- a/spec/views/idv/phone_errors/timeout.html.erb_spec.rb +++ b/spec/views/idv/phone_errors/timeout.html.erb_spec.rb @@ -2,14 +2,12 @@ describe 'idv/phone_errors/timeout.html.erb' do let(:sp_name) { 'Example SP' } - let(:enable_gpo_verification) { false } + let(:gpo_letter_available) { false } before do - allow(FeatureManagement).to receive(:enable_gpo_verification?). - and_return(enable_gpo_verification) - decorated_session = instance_double(ServiceProviderSessionDecorator, sp_name: sp_name) allow(view).to receive(:decorated_session).and_return(decorated_session) + assign(:gpo_letter_available, gpo_letter_available) render end @@ -43,7 +41,7 @@ end context 'gpo verification enabled' do - let(:enable_gpo_verification) { true } + let(:gpo_letter_available) { true } it 'renders a list of troubleshooting options' do expect(rendered).to have_link( diff --git a/spec/views/idv/phone_errors/warning.html.erb_spec.rb b/spec/views/idv/phone_errors/warning.html.erb_spec.rb index 10a83fefed9..71e20bc0a2e 100644 --- a/spec/views/idv/phone_errors/warning.html.erb_spec.rb +++ b/spec/views/idv/phone_errors/warning.html.erb_spec.rb @@ -3,14 +3,12 @@ describe 'idv/phone_errors/warning.html.erb' do let(:sp_name) { 'Example SP' } let(:remaining_attempts) { 5 } - let(:enable_gpo_verification) { false } + let(:gpo_letter_available) { false } before do - allow(FeatureManagement).to receive(:enable_gpo_verification?). - and_return(enable_gpo_verification) - decorated_session = instance_double(ServiceProviderSessionDecorator, sp_name: sp_name) allow(view).to receive(:decorated_session).and_return(decorated_session) + assign(:gpo_letter_available, gpo_letter_available) assign(:remaining_attempts, remaining_attempts) @@ -43,7 +41,7 @@ end context 'gpo verification enabled' do - let(:enable_gpo_verification) { true } + let(:gpo_letter_available) { true } it 'renders a list of troubleshooting options' do expect(rendered).to have_link(