diff --git a/src/views/oauth/OAuthError.js b/src/views/oauth/OAuthError.js index 93a553e57e..64c32282bd 100644 --- a/src/views/oauth/OAuthError.js +++ b/src/views/oauth/OAuthError.js @@ -16,12 +16,14 @@ import { SlideDown } from 'src/components/SlideDown' import { getDelay } from 'src/utilities/getDelay' import { PostMessageContext } from 'src/ConnectWidget' import { getSelectedInstitution } from 'src/redux/selectors/Connect' +import { selectConnectConfig } from 'src/redux/reducers/configSlice' export const OAuthError = React.forwardRef((props, navigationRef) => { useAnalyticsPath(...PageviewInfo.CONNECT_OAUTH_ERROR) const { currentMember, onRetry, onReturnToSearch } = props const postMessageFunctions = useContext(PostMessageContext) + const connectConfig = useSelector(selectConnectConfig) const errorReason = useSelector((state) => state.connect.oauthErrorReason) const selectedInstitution = useSelector(getSelectedInstitution) const tokens = useTokens() @@ -35,10 +37,13 @@ export const OAuthError = React.forwardRef((props, navigationRef) => { onReturnToSearch() }, showBackButton() { - return true + // Going back leads to the institution search, which is not available + // when disable_institution_search is set. The "Try again" button + // remains as the primary action. + return !connectConfig.disable_institution_search }, } - }, []) + }, [connectConfig.disable_institution_search]) // If we have an oauth error, send the post message. useEffect(() => { diff --git a/src/views/oauth/OAuthStep.js b/src/views/oauth/OAuthStep.js index 9e7b936c63..49f48abb9d 100644 --- a/src/views/oauth/OAuthStep.js +++ b/src/views/oauth/OAuthStep.js @@ -78,10 +78,22 @@ export const OAuthStep = React.forwardRef((props, navigationRef) => { } }, showBackButton() { - return true + // The interstitial disclosure and waiting views handle "back" within this + // step, so the back button stays available for them. Otherwise, going back + // leads to the institution search, which is not available when + // disable_institution_search is set. + if (showInterstitialDisclosure || isWaitingForOAuth) { + return true + } + return !config.disable_institution_search }, } - }, [isWaitingForOAuth, oauthStartError, showInterstitialDisclosure]) + }, [ + isWaitingForOAuth, + oauthStartError, + showInterstitialDisclosure, + config.disable_institution_search, + ]) /** * Called when we succesfully generate an oauth window uri for the exsting diff --git a/src/views/oauth/__tests__/OAuthError-test.tsx b/src/views/oauth/__tests__/OAuthError-test.tsx index 456b50aa36..eecb03b102 100644 --- a/src/views/oauth/__tests__/OAuthError-test.tsx +++ b/src/views/oauth/__tests__/OAuthError-test.tsx @@ -3,7 +3,9 @@ import { render, screen, waitFor } from 'src/utilities/testingLibrary' import { OAuthError, getOAuthErrorMessage } from 'src/views/oauth/OAuthError' import { OAUTH_ERROR_REASONS } from 'src/const/Connect' -import { institutionData } from 'src/services/mockedData' +import { initialState as mockedState, institutionData } from 'src/services/mockedData' + +type NavigationHandle = { handleBackButton: () => void; showBackButton: () => boolean } describe('OAuthError', () => { const defaultProps = { @@ -33,6 +35,29 @@ describe('OAuthError', () => { expect(defaultProps.onRetry).toHaveBeenCalledTimes(1) }) + it('shows the navigation back button by default', () => { + const ref = React.createRef() + + render(, { + preloadedState: initialState, + }) + + expect(ref.current?.showBackButton()).toBe(true) + }) + + it('hides the navigation back button when disable_institution_search is true', () => { + const ref = React.createRef() + + render(, { + preloadedState: { + ...initialState, + config: { ...mockedState.config, disable_institution_search: true }, + }, + }) + + expect(ref.current?.showBackButton()).toBe(false) + }) + describe('getOAuthErrorMessage util', () => { it('DEFAULT message is returned when given a blank reason', () => { expect(getOAuthErrorMessage('Default/Fallback')).toEqual( diff --git a/src/views/oauth/__tests__/OAuthStep-test.tsx b/src/views/oauth/__tests__/OAuthStep-test.tsx index c70460582c..acc15664d7 100644 --- a/src/views/oauth/__tests__/OAuthStep-test.tsx +++ b/src/views/oauth/__tests__/OAuthStep-test.tsx @@ -3,7 +3,9 @@ import { render, screen, waitFor } from 'src/utilities/testingLibrary' import { OAuthStep } from 'src/views/oauth/OAuthStep' import { apiValue } from 'src/const/apiProviderMock' import { ApiProvider } from 'src/context/ApiContext' -import { OAUTH_STATE } from 'src/services/mockedData' +import { initialState, OAUTH_STATE } from 'src/services/mockedData' + +type NavigationHandle = { handleBackButton: () => void; showBackButton: () => boolean } describe('OauthStep view', () => { describe('Ensure OAuthDefault is rendered', () => { @@ -111,4 +113,55 @@ describe('OauthStep view', () => { ) }, 35000) }) + + describe('showBackButton', () => { + const defaultProps = { + institution: { guid: 'INS-123', name: 'MX Bank', instructional_data: {} }, + onGoBack: vi.fn(), + } + + const renderOAuthStep = async (configOverrides = {}) => { + const ref = React.createRef() + const { user } = render( + + + , + { + preloadedState: { + config: { ...initialState.config, ...configOverrides }, + connect: { + members: [], + currentMemberGuid: null, + location: [{ step: 'ENTER_CREDENTIALS' }], + }, + }, + }, + ) + + await screen.findByTestId('continue-button') + + return { ref, user } + } + + it('shows the back button by default', async () => { + const { ref } = await renderOAuthStep() + + expect(ref.current?.showBackButton()).toBe(true) + }) + + it('hides the back button when disable_institution_search is true', async () => { + const { ref } = await renderOAuthStep({ disable_institution_search: true }) + + expect(ref.current?.showBackButton()).toBe(false) + }) + + it('still shows the back button while waiting for OAuth when disable_institution_search is true', async () => { + const { ref, user } = await renderOAuthStep({ disable_institution_search: true }) + + await user.click(screen.getByTestId('continue-button')) + await screen.findByRole('button', { name: 'Try again' }) + + expect(ref.current?.showBackButton()).toBe(true) + }) + }) })