From 12519feadab1509efa94acfe009ea1fd9fb6dd9e Mon Sep 17 00:00:00 2001 From: Suraj Karambe Date: Wed, 20 Sep 2023 19:23:13 +0530 Subject: [PATCH 1/4] Updated validate user reg request action type --- login-workflow/docs/API.md | 2 +- login-workflow/docs/registration-workflow.md | 2 +- .../src/actions/RegistrationUIActions.tsx | 7 ++++-- .../RegistrationWorkflow.tsx | 3 ++- .../src/contexts/RegistrationContext/types.ts | 5 +++- .../VerifyCodeScreen/VerifyCodeScreen.tsx | 23 ++++++++++++++----- 6 files changed, 30 insertions(+), 12 deletions(-) diff --git a/login-workflow/docs/API.md b/login-workflow/docs/API.md index 497895c0..70c6ed48 100644 --- a/login-workflow/docs/API.md +++ b/login-workflow/docs/API.md @@ -27,7 +27,7 @@ The `RegistrationContextProvider` manages the state of the registration workflow - A function that is used to accept the EULA. This function will be called when the user clicks the Next button on the EULA screen. - **requestRegistrationCode**: _`(email: string) => Promise`_ - A function that is used to request a registration code. This function will be called when the user lands on the Verify Code screen as well as when a user clicks the Resend Verification Code button. -- **validateUserRegistrationRequest**: _`(validationCode: string, validationEmail?: string) => Promise`_ +- **validateUserRegistrationRequest**: _`(validationCode: string, validationEmail?: string) => Promise<{codeValid: boolean | string; accountExists?: boolean}>`_ - A function that is used to validate a registration code. This function will be called when the user clicks the Next button on the Verify Code screen screen. - **createPassword**: _`(password: string) => Promise`_ - A function that is used to create a password. This function will be called when the user clicks the Next button on the Create Password screen. diff --git a/login-workflow/docs/registration-workflow.md b/login-workflow/docs/registration-workflow.md index e3eea4f0..cd320f56 100644 --- a/login-workflow/docs/registration-workflow.md +++ b/login-workflow/docs/registration-workflow.md @@ -79,7 +79,7 @@ For a detailed explanation of setting up routes, see the [Routing](./routing.md) | loadEula | `(language: string) => Promise` | A function that is used to load the Eula content. This function will be called when the Eula screen is loaded. | | | acceptEula | `() => Promise` | A function that is called when the user has accepted the Eula and hit the Next button. | | | requestRegistrationCode | `(email: string) => Promise` | A function that is used to request a registration code. This function will be called when the user clicks the Next button on the Create Account screen or Resend button on Verify Code screen. | | -| validateUserRegistrationRequest | `(validationCode: string, validationEmail?: string) => Promise` | A function that is used to verify registration code. This function will be called when the user clicks the Next button on the Verify Code screen. | | +| validateUserRegistrationRequest | `(validationCode: string, validationEmail?: string) => Promise<{codeValid: boolean | string; accountExists?: boolean}>` | A function that is used to verify registration code. This function will be called when the user clicks the Next button on the Verify Code screen. | | | createPassword | `(password: string) => Promise` | A function that is used to create password. This function will be called when the user clicks the Next button on the Create Password screen. | | | setAccountDetails | `(details: { firstName: string; lastName: string; extra?: { [key: string]: boolean \| string \| number }}) => Promise` | A function that is used to set account details. This function will be called when the user clicks the Next button on the Account Details screen. | | | completeRegistration | `(userData: any, validationCode: number \| string, validationEmail: string) => Promise<{ email: string; organizationName: string }>` | A function that is used to complete the registration workflow. This function will be called when the user clicks the Next button on the last registration workflow screen. | | diff --git a/login-workflow/example/src/actions/RegistrationUIActions.tsx b/login-workflow/example/src/actions/RegistrationUIActions.tsx index 615aad89..200b593b 100644 --- a/login-workflow/example/src/actions/RegistrationUIActions.tsx +++ b/login-workflow/example/src/actions/RegistrationUIActions.tsx @@ -92,13 +92,16 @@ export const ProjectRegistrationUIActions: () => RegistrationUIActions = () => ( * @returns Resolves when the code is valid. True if registration is complete, False if account information is needed. * If the code is not valid a rejection will occur with an error message. */ - validateUserRegistrationRequest: async (validationCode: string, validationEmail?: string): Promise => { + validateUserRegistrationRequest: async ( + validationCode: string, + validationEmail?: string + ): Promise<{ codeValid: boolean | string; accountExists?: boolean }> => { await sleep(800); if (isRandomFailure()) { throw new Error('Sorry, there was a problem sending your request.'); } - return isRandomFailure(); + return { codeValid: true, accountExists: false }; }, completeRegistration: async (userData: object): Promise<{ email: string; organizationName: string }> => { diff --git a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx index 857b8cef..e8d917ce 100644 --- a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx +++ b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx @@ -169,7 +169,8 @@ export const RegistrationWorkflow: React.FC => { try { - isAccExist = await actions.validateUserRegistrationRequest(params.code, params.email); + const { accountExists } = await actions.validateUserRegistrationRequest(params.code, params.email); + isAccExist = accountExists; } catch (_error) { triggerError(_error as Error); } finally { diff --git a/login-workflow/src/contexts/RegistrationContext/types.ts b/login-workflow/src/contexts/RegistrationContext/types.ts index 338a9174..102f7f1b 100644 --- a/login-workflow/src/contexts/RegistrationContext/types.ts +++ b/login-workflow/src/contexts/RegistrationContext/types.ts @@ -37,7 +37,10 @@ export type RegistrationUIActions = { * @param {string} validationEmail - the provided email address * @returns Promise */ - validateUserRegistrationRequest?: (validationCode: string, validationEmail?: string) => Promise; + validateUserRegistrationRequest?: ( + validationCode: string, + validationEmail?: string + ) => Promise<{ codeValid: boolean | string; accountExists?: boolean }>; /** * A function that is used to create a password. This function will be called when the user clicks the Next button on the Create Password screen diff --git a/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx b/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx index d3f70f14..6a697376 100644 --- a/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx +++ b/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx @@ -72,12 +72,23 @@ export const VerifyCodeScreen: React.FC = (props) => { async (code: string) => { try { setIsLoading(true); - const isAccExist = await actions.validateUserRegistrationRequest(code); - void nextScreen({ - screenId: 'VerifyCode', - values: { code: code }, - isAccountExist: isAccExist, - }); + const { codeValid, accountExists } = await actions.validateUserRegistrationRequest(code); + + if (typeof codeValid === 'boolean') { + if (codeValid) + void nextScreen({ + screenId: 'VerifyCode', + values: { code }, + isAccountExist: accountExists, + }); + else { + triggerError( + new Error(t('bluiRegistration:SELF_REGISTRATION.VERIFY_EMAIL.CODE_VALIDATOR_ERROR')) + ); + } + } else { + triggerError(new Error(codeValid)); + } } catch (_error) { triggerError(_error as Error); } finally { From 257f315cce43a09bdb6b98198212e6fa8f52e1e8 Mon Sep 17 00:00:00 2001 From: Suraj Karambe Date: Thu, 21 Sep 2023 12:42:21 +0530 Subject: [PATCH 2/4] Updated invite registration workflow to use updated validateUserRegistrationRequest --- .../RegistrationWorkflow.tsx | 19 +++++++++++++++++-- .../VerifyCodeScreen/VerifyCodeScreen.tsx | 2 +- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx index e8d917ce..cdfa8c9e 100644 --- a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx +++ b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx @@ -12,6 +12,7 @@ import { import { parseQueryString } from '../../utils'; import { useErrorManager } from '../../contexts/ErrorContext/useErrorManager'; import ErrorManager, { ErrorManagerProps } from '../Error/ErrorManager'; +import { useLanguageLocale } from '../../hooks'; /** * Component that contain the registration workflow and index of screens. @@ -56,12 +57,16 @@ export type RegistrationWorkflowProps = { export const RegistrationWorkflow: React.FC> = (props) => { const [isAccountExist, setIsAccountExist] = useState(false); const { triggerError, errorManagerConfig } = useErrorManager(); + const { t } = useLanguageLocale(); + const { actions, navigate } = useRegistrationContext(); + const errorDisplayConfig = { ...errorManagerConfig, ...props.errorDisplayConfig, onClose: (): void => { if (props.errorDisplayConfig && props.errorDisplayConfig.onClose) props.errorDisplayConfig.onClose(); if (errorManagerConfig.onClose) errorManagerConfig?.onClose(); + navigate(-1); }, }; const { @@ -90,7 +95,6 @@ export const RegistrationWorkflow: React.FC totalScreens - 1 ? totalScreens - 1 : initialScreenIndex ); const [showSuccessScreen, setShowSuccessScreen] = useState(false); - const { actions, navigate } = useRegistrationContext(); const [screenData, setScreenData] = useState({ Eula: { @@ -169,8 +173,19 @@ export const RegistrationWorkflow: React.FC => { try { - const { accountExists } = await actions.validateUserRegistrationRequest(params.code, params.email); + const { codeValid, accountExists } = await actions.validateUserRegistrationRequest( + params.code, + params.email + ); isAccExist = accountExists; + + if (typeof codeValid === 'string') { + triggerError(new Error(codeValid)); + } else if (typeof codeValid === 'boolean' && !codeValid) { + triggerError( + new Error(t('bluiRegistration:SELF_REGISTRATION.VERIFY_EMAIL.CODE_VALIDATOR_ERROR')) + ); + } } catch (_error) { triggerError(_error as Error); } finally { diff --git a/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx b/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx index 6a697376..da02203f 100644 --- a/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx +++ b/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx @@ -95,7 +95,7 @@ export const VerifyCodeScreen: React.FC = (props) => { setIsLoading(false); } }, - [actions, nextScreen, triggerError] + [t, actions, nextScreen, triggerError] ); const onPrevious = (code: string): void => { From 912f87cca7e666df0fb057f95e980b47f249821e Mon Sep 17 00:00:00 2001 From: Suraj Karambe Date: Thu, 21 Sep 2023 14:03:24 +0530 Subject: [PATCH 3/4] Updated logic for account already exists for invite / self reg --- .../RegistrationWorkflow.tsx | 14 ++++---- .../VerifyCodeScreen/VerifyCodeScreen.tsx | 32 +++++++++++-------- 2 files changed, 26 insertions(+), 20 deletions(-) diff --git a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx index cdfa8c9e..b473442b 100644 --- a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx +++ b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx @@ -179,12 +179,14 @@ export const RegistrationWorkflow: React.FC = (props) => { const { t } = useLanguageLocale(); const regWorkflow = useRegistrationWorkflowContext(); const { actions } = useRegistrationContext(); - const { nextScreen, previousScreen, screenData, currentScreen, totalScreens } = regWorkflow; + const { nextScreen, previousScreen, screenData, currentScreen, totalScreens, updateScreenData } = regWorkflow; const { emailAddress } = screenData.CreateAccount; const { triggerError, errorManagerConfig } = useErrorManager(); const errorDisplayConfig = { @@ -74,20 +74,24 @@ export const VerifyCodeScreen: React.FC = (props) => { setIsLoading(true); const { codeValid, accountExists } = await actions.validateUserRegistrationRequest(code); - if (typeof codeValid === 'boolean') { - if (codeValid) - void nextScreen({ - screenId: 'VerifyCode', - values: { code }, - isAccountExist: accountExists, - }); - else { - triggerError( - new Error(t('bluiRegistration:SELF_REGISTRATION.VERIFY_EMAIL.CODE_VALIDATOR_ERROR')) - ); - } + if (accountExists) { + updateScreenData({ screenId: 'VerifyCode', values: { code }, isAccountExist: accountExists }); } else { - triggerError(new Error(codeValid)); + if (typeof codeValid === 'boolean') { + if (codeValid) + void nextScreen({ + screenId: 'VerifyCode', + values: { code }, + isAccountExist: accountExists, + }); + else { + triggerError( + new Error(t('bluiRegistration:SELF_REGISTRATION.VERIFY_EMAIL.CODE_VALIDATOR_ERROR')) + ); + } + } else { + triggerError(new Error(codeValid)); + } } } catch (_error) { triggerError(_error as Error); From 83269f04d25d81950f9c7845fe61c8e2b20f642c Mon Sep 17 00:00:00 2001 From: Suraj Karambe Date: Thu, 21 Sep 2023 20:07:53 +0530 Subject: [PATCH 4/4] Updated updateScreenData function to handle account already exists --- .../RegistrationWorkflow/RegistrationWorkflow.tsx | 6 +++++- .../src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx | 2 +- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx index b473442b..372eceb8 100644 --- a/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx +++ b/login-workflow/src/components/RegistrationWorkflow/RegistrationWorkflow.tsx @@ -120,7 +120,11 @@ export const RegistrationWorkflow: React.FC { const { Other }: { [key: string]: any } = screenData; - const { screenId, values } = data; + const { screenId, values, isAccountExist: accountExists } = data; + + setIsAccountExist(accountExists); + setShowSuccessScreen(accountExists); + if (!Object.keys(screenData).includes(screenId)) { setScreenData((oldData) => ({ ...oldData, diff --git a/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx b/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx index a3154541..e8e82669 100644 --- a/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx +++ b/login-workflow/src/screens/VerifyCodeScreen/VerifyCodeScreen.tsx @@ -99,7 +99,7 @@ export const VerifyCodeScreen: React.FC = (props) => { setIsLoading(false); } }, - [t, actions, nextScreen, triggerError] + [t, actions, nextScreen, triggerError, updateScreenData] ); const onPrevious = (code: string): void => {