diff --git a/src/constants/translations/en/edit-profile.json b/src/constants/translations/en/edit-profile.json
index f1d42b1fa..543bceee7 100644
--- a/src/constants/translations/en/edit-profile.json
+++ b/src/constants/translations/en/edit-profile.json
@@ -72,13 +72,15 @@
"passwordSecurityTab": {
"tabTitle": "Password & Security",
"title": "Password & Security",
+ "subTitle": "You can change your password using the current one.",
"description": "Change password and security settings",
"changePassword": "Change password",
+ "changePasswordModalDescription": "Reset your current password to new one.",
"changePasswordConfirm": "Are you sure you want to change the password?",
"currentPassword": "Current password",
"newPassword": "New password",
"retypePassword": "Re-type new password",
- "savePassword": "Save new password",
+ "savePassword": "Save the password",
"deactivateAccount": "Deactivate account",
"deactivateBtn": "Deactivate",
"deactivateTitle": "Deactivate your account?",
diff --git a/src/constants/translations/uk/edit-profile.json b/src/constants/translations/uk/edit-profile.json
index 15775a79c..d1d724a57 100644
--- a/src/constants/translations/uk/edit-profile.json
+++ b/src/constants/translations/uk/edit-profile.json
@@ -72,8 +72,10 @@
"passwordSecurityTab": {
"tabTitle": "Пароль і Безпека",
"title": "Пароль і Безпека",
+ "subTitle": "Ви можете змінити свій пароль, використовуючи поточний.",
"description": "Зміна паролю та налаштуваннь безпеки",
"changePassword": "Змінити пароль",
+ "changePasswordModalDescription": "Змінити поточний пароль на новий.",
"changePasswordConfirm": "Ви впевнені, що бажаєте змінити пароль?",
"currentPassword": "Поточний пароль",
"newPassword": "Новий пароль",
diff --git a/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.styles.ts b/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.styles.ts
index 768375f7d..17725fb65 100644
--- a/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.styles.ts
+++ b/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.styles.ts
@@ -4,14 +4,12 @@ import { rootContainer } from '~/containers/edit-profile/common.styles'
export const styles = {
container: rootContainer,
titleAndDescription: {
- title: {
- typography: TypographyVariantEnum.H6
- },
- description: {
- typography: TypographyVariantEnum.Body2,
- color: 'primary.500',
- mb: '30px'
- }
+ typography: TypographyVariantEnum.H5
+ },
+ description: {
+ typography: TypographyVariantEnum.Subtitle1,
+ color: 'primary.500',
+ mb: '30px'
},
subtitle: {
typography: TypographyVariantEnum.Body1,
@@ -20,13 +18,9 @@ export const styles = {
form: { display: 'flex', flexDirection: 'column', gap: '8px' },
passwordButtonsContainer: {
- m: '10px 0 20px',
- display: 'grid',
- gridTemplateColumns: {
- sm: 'repeat(5, minmax(0, 1fr))',
- md: 'repeat(7, minmax(0, 1fr))',
- lg: 'repeat(10, minmax(0, 1fr))'
- },
+ display: 'flex',
+ justifyContent: 'flex-end',
+ alignItems: 'flex-end',
gap: '10px'
},
@@ -39,5 +33,12 @@ export const styles = {
deactivateButton: {
mt: '20px',
backgroundColor: 'error.700'
+ },
+ modalContainer: {
+ display: 'flex',
+ alignItems: 'center',
+ justifyContent: 'center',
+ width: '700px',
+ position: 'relative'
}
}
diff --git a/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.tsx b/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.tsx
index 8ba263a83..a7b8b59fe 100644
--- a/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.tsx
+++ b/src/containers/edit-profile/password-security-tab/PasswordSecurityTab.tsx
@@ -1,113 +1,26 @@
-import { useCallback, FC } from 'react'
+import { FC } from 'react'
import { useTranslation } from 'react-i18next'
-
import Box from '@mui/material/Box'
-import Typography from '@mui/material/Typography'
-import Divider from '@mui/material/Divider'
-
-import Loader from '~/components/loader/Loader'
-import AppButton from '~/components/app-button/AppButton'
-import AppTextField from '~/components/app-text-field/AppTextField'
-import TitleWithDescription from '~/components/title-with-description/TitleWithDescription'
-import { snackbarVariants } from '~/constants'
-import useForm from '~/hooks/use-form'
+import { useModalContext } from '~/context/modal-context'
import useChangeUserStatus from '~/hooks/use-change-user-status'
-import useAxios from '~/hooks/use-axios'
-import { useAppDispatch, useAppSelector } from '~/hooks/use-redux'
-import useInputVisibility from '~/hooks/use-input-visibility'
-import useConfirm from '~/hooks/use-confirm'
-
-import { AuthService } from '~/services/auth-service'
-import { openAlert } from '~/redux/features/snackbarSlice'
+import PasswordSecurityItem from '~/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem'
+import ChangePasswordModal from '~/containers/edit-profile/password-security-tab/change-password-modal/ChangePasswordModal'
+import AppButton from '~/components/app-button/AppButton'
import { styles } from '~/containers/edit-profile/password-security-tab/PasswordSecurityTab.styles'
-
-import {
- ButtonVariantEnum,
- ComponentEnum,
- ButtonTypeEnum,
- InputEnum,
- SizeEnum,
- FormValues,
- ErrorResponse
-} from '~/types'
-import {
- initialValues,
- validations
-} from '~/containers/edit-profile/password-security-tab/PasswordSecurityTab.constants'
+import { ButtonVariantEnum, SizeEnum } from '~/types'
const PasswordSecurityTab: FC = () => {
const { t } = useTranslation()
- const dispatch = useAppDispatch()
- const { userId } = useAppSelector((state) => state.appMain)
- const { checkConfirmation } = useConfirm()
-
+ const { openModal } = useModalContext()
const { neededAction, checkStatusChange } = useChangeUserStatus()
- const handleSubmitChangePassword = async () => {
- const confirmed = await checkConfirmation({
- message: t(
- 'editProfilePage.profile.passwordSecurityTab.changePasswordConfirm'
- ),
- title: 'titles.confirmTitle',
- check: true
+ const openChangePasswordModal = () => {
+ openModal({
+ component:
})
- if (confirmed) {
- resetErrors()
- await sendChangedPassword({
- password: data.password,
- currentPassword: data.currentPassword
- })
- }
- }
-
- const handleResponse = () => {
- dispatch(
- openAlert({
- severity: snackbarVariants.success,
- message: 'editProfilePage.profile.successMessage'
- })
- )
- }
-
- const changePassword = useCallback(
- (data: { password: string; currentPassword: string }) => {
- return AuthService.changePassword(userId, data)
- },
- [userId]
- )
-
- const handleResponseError = (error?: ErrorResponse) => {
- if (error?.code === 'INCORRECT_CREDENTIALS') {
- handleErrors('password', t('common.errorMessages.samePasswords'))
- } else {
- handleErrors('currentPassword', t('common.errorMessages.currentPassword'))
- }
}
-
- const { loading, fetchData: sendChangedPassword } = useAxios({
- service: changePassword,
- onResponse: handleResponse,
- onResponseError: handleResponseError,
- fetchOnMount: false
- })
-
- const {
- data,
- handleSubmit,
- handleInputChange,
- errors,
- handleBlur,
- resetData,
- resetErrors,
- handleErrors
- } = useForm({
- onSubmit: handleSubmitChangePassword,
- initialValues: initialValues,
- validations: validations
- })
-
const handleChangeStatusClick = () => {
void checkStatusChange(
`editProfilePage.profile.passwordSecurityTab.${neededAction}Title`,
@@ -115,113 +28,27 @@ const PasswordSecurityTab: FC = () => {
true
)
}
-
- const {
- inputVisibility: currentPasswordVisibility,
- showInputText: showCurrentPassword
- } = useInputVisibility(errors.currentPassword)
-
- const { inputVisibility: passwordVisibility, showInputText: showPassword } =
- useInputVisibility(errors.password)
-
- const {
- inputVisibility: newPasswordVisibility,
- showInputText: showNewPassword
- } = useInputVisibility(errors.confirmPassword)
-
- const onDiscard = () => {
- resetData()
- resetErrors()
- }
-
- const saveButtonContent = loading ? (
-
- ) : (
- t('editProfilePage.profile.passwordSecurityTab.savePassword')
- )
-
- const inputType = (isVisible: boolean) =>
- isVisible ? InputEnum.Text : InputEnum.Password
-
return (
-
-
+
-
-
- {t('editProfilePage.profile.passwordSecurityTab.changePassword')}
-
-
-
-
-
-
-
-
- {saveButtonContent}
-
-
- {t('common.discard')}
-
-
-
-
- {t(
- `editProfilePage.profile.passwordSecurityTab.${neededAction}Account`
- )}
-
-
+
+ {t(
+ `editProfilePage.profile.passwordSecurityTab.${neededAction}Account`
+ )}
+
)
}
diff --git a/src/containers/edit-profile/password-security-tab/change-password-modal/ChangePasswordModal.tsx b/src/containers/edit-profile/password-security-tab/change-password-modal/ChangePasswordModal.tsx
new file mode 100644
index 000000000..7016e786a
--- /dev/null
+++ b/src/containers/edit-profile/password-security-tab/change-password-modal/ChangePasswordModal.tsx
@@ -0,0 +1,211 @@
+import { useCallback } from 'react'
+import { useTranslation } from 'react-i18next'
+import Box from '@mui/material/Box'
+import Typography from '@mui/material/Typography'
+
+import { useModalContext } from '~/context/modal-context'
+import { AuthService } from '~/services/auth-service'
+import useForm from '~/hooks/use-form'
+import useAxios from '~/hooks/use-axios'
+import useInputVisibility from '~/hooks/use-input-visibility'
+import useConfirm from '~/hooks/use-confirm'
+
+import Loader from '~/components/loader/Loader'
+import AppButton from '~/components/app-button/AppButton'
+import AppTextField from '~/components/app-text-field/AppTextField'
+
+import { snackbarVariants } from '~/constants'
+
+import { useAppDispatch, useAppSelector } from '~/hooks/use-redux'
+import { openAlert } from '~/redux/features/snackbarSlice'
+
+import { styles } from '~/containers/edit-profile/password-security-tab/PasswordSecurityTab.styles'
+
+import {
+ ButtonVariantEnum,
+ ComponentEnum,
+ ButtonTypeEnum,
+ InputEnum,
+ SizeEnum,
+ FormValues,
+ ErrorResponse
+} from '~/types'
+import {
+ initialValues,
+ validations
+} from '~/containers/edit-profile/password-security-tab/PasswordSecurityTab.constants'
+
+const ChangePasswordModal = () => {
+ const { t } = useTranslation()
+ const dispatch = useAppDispatch()
+ const { userId } = useAppSelector((state) => state.appMain)
+ const { checkConfirmation } = useConfirm()
+ const { closeModal } = useModalContext()
+
+ const handleSubmitChangePassword = async () => {
+ const confirmed = await checkConfirmation({
+ message: t(
+ 'editProfilePage.profile.passwordSecurityTab.changePasswordConfirm'
+ ),
+ title: 'titles.confirmTitle',
+ check: true
+ })
+ if (confirmed) {
+ resetErrors()
+ await sendChangedPassword({
+ password: data.password,
+ currentPassword: data.currentPassword
+ })
+ }
+ }
+
+ const handleResponse = () => {
+ dispatch(
+ openAlert({
+ severity: snackbarVariants.success,
+ message: 'editProfilePage.profile.successMessage'
+ })
+ )
+ closeModal()
+ }
+
+ const changePassword = useCallback(
+ (data: { password: string; currentPassword: string }) => {
+ return AuthService.changePassword(userId, data)
+ },
+ [userId]
+ )
+
+ const handleResponseError = (error?: ErrorResponse) => {
+ if (error?.code === 'INCORRECT_CREDENTIALS') {
+ handleErrors('password', t('common.errorMessages.samePasswords'))
+ } else {
+ handleErrors('currentPassword', t('common.errorMessages.currentPassword'))
+ }
+ }
+
+ const { loading, fetchData: sendChangedPassword } = useAxios({
+ service: changePassword,
+ onResponse: handleResponse,
+ onResponseError: handleResponseError,
+ fetchOnMount: false
+ })
+
+ const {
+ data,
+ handleSubmit,
+ handleInputChange,
+ errors,
+ handleBlur,
+ resetData,
+ resetErrors,
+ handleErrors
+ } = useForm({
+ onSubmit: handleSubmitChangePassword,
+ initialValues: initialValues,
+ validations: validations
+ })
+
+ const {
+ inputVisibility: currentPasswordVisibility,
+ showInputText: showCurrentPassword
+ } = useInputVisibility(errors.currentPassword)
+
+ const { inputVisibility: passwordVisibility, showInputText: showPassword } =
+ useInputVisibility(errors.password)
+
+ const {
+ inputVisibility: newPasswordVisibility,
+ showInputText: showNewPassword
+ } = useInputVisibility(errors.confirmPassword)
+
+ const onDiscard = () => {
+ resetData()
+ resetErrors()
+ closeModal()
+ }
+
+ const saveButtonContent = loading ? (
+
+ ) : (
+ t('editProfilePage.profile.passwordSecurityTab.savePassword')
+ )
+
+ const inputType = (isVisible: boolean) =>
+ isVisible ? InputEnum.Text : InputEnum.Password
+
+ return (
+
+
+
+ {t('editProfilePage.profile.passwordSecurityTab.changePassword')}
+
+
+ {t(
+ 'editProfilePage.profile.passwordSecurityTab.changePasswordModalDescription'
+ )}
+
+
+
+
+
+
+
+
+
+ {t('common.cancel')}
+
+
+ {saveButtonContent}
+
+
+
+
+
+ )
+}
+
+export default ChangePasswordModal
diff --git a/src/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.styles.ts b/src/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.styles.ts
new file mode 100644
index 000000000..b1af738ef
--- /dev/null
+++ b/src/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.styles.ts
@@ -0,0 +1,20 @@
+import { TypographyVariantEnum } from '~/types'
+
+export const styles = {
+ container: {
+ display: 'flex',
+ justifyContent: 'space-between',
+ alignItems: 'flex-start',
+ m: '20px 0'
+ },
+ title: {
+ typography: TypographyVariantEnum.Button
+ },
+ description: {
+ typography: TypographyVariantEnum.Body2,
+ color: 'primary.500'
+ },
+ titlesAndButtonContainer: {
+ p: '20px 0'
+ }
+}
diff --git a/src/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.tsx b/src/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.tsx
new file mode 100644
index 000000000..f52497684
--- /dev/null
+++ b/src/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.tsx
@@ -0,0 +1,44 @@
+import { SxProps } from '@mui/material'
+import Box from '@mui/material/Box'
+import Typography from '@mui/material/Typography'
+import { Theme } from '@emotion/react'
+
+import AppButton from '~/components/app-button/AppButton'
+import AppCard from '~/components/app-card/AppCard'
+
+import { styles } from '~/containers/edit-profile/password-security-tab/password-security-item/PasswordSecurityItem.styles'
+import { ButtonVariantEnum, SizeEnum } from '~/types'
+
+interface PasswordSecurityItemProps {
+ title: string
+ description: string
+ buttonText: string
+ onClick: () => void
+ sx?: SxProps
+}
+
+const PasswordSecurityItem = ({
+ title,
+ description,
+ buttonText,
+ onClick,
+ sx
+}: PasswordSecurityItemProps) => (
+
+
+ {title}
+ {description}
+
+
+
+ {buttonText}
+
+
+)
+
+export default PasswordSecurityItem
diff --git a/tests/unit/containers/edit-profile/password-security-tab/ChangePasswordModal.spec.jsx b/tests/unit/containers/edit-profile/password-security-tab/ChangePasswordModal.spec.jsx
new file mode 100644
index 000000000..d466cc8fb
--- /dev/null
+++ b/tests/unit/containers/edit-profile/password-security-tab/ChangePasswordModal.spec.jsx
@@ -0,0 +1,200 @@
+import { vi } from 'vitest'
+import { screen, fireEvent, waitFor } from '@testing-library/react'
+import {
+ renderWithProviders,
+ mockAxiosClient,
+ TestSnackbar
+} from '~tests/test-utils'
+import ChangePasswordModal from '~/containers/edit-profile/password-security-tab/change-password-modal/ChangePasswordModal'
+import { AuthService } from '~/services/auth-service'
+import { URLs } from '~/constants/request'
+
+const userDataMock = {
+ _id: 123456
+}
+
+const handleSubmit = vi.fn()
+
+vi.mock('~/services/auth-service', () => ({
+ AuthService: {
+ changePassword: vi.fn()
+ }
+}))
+
+const renderChangePasswordModal = () => {
+ renderWithProviders(
+
+
+ ,
+ {
+ preloadedState: {
+ appMain: {
+ userId: userDataMock._id,
+ userStatus: 'active'
+ }
+ }
+ }
+ )
+}
+
+describe('ChangePasswordModal', () => {
+ beforeEach(() => {
+ renderChangePasswordModal()
+ })
+
+ it('should save data after positive response', async () => {
+ mockAxiosClient
+ .onPatch(`${URLs.auth.changePassword}/${userDataMock._id}`)
+ .reply(200)
+
+ const currentPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.currentPassword/i
+ )
+ const passwordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.newPassword/i
+ )
+ const confirmPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.retypePassword/i
+ )
+ const saveButton = screen.getByText(
+ /editProfilePage.profile.passwordSecurityTab.savePassword/i
+ )
+
+ fireEvent.change(currentPasswordInput, {
+ target: { value: '12345qwert' }
+ })
+ fireEvent.change(passwordInput, {
+ target: { value: '12345qwertY' }
+ })
+ fireEvent.change(confirmPasswordInput, {
+ target: { value: '12345qwertY' }
+ })
+
+ await waitFor(() => {
+ fireEvent.click(saveButton)
+ })
+
+ const confirmButton = screen.getByText('common.yes')
+ fireEvent.click(confirmButton)
+
+ await waitFor(() => {
+ expect(AuthService.changePassword).toHaveBeenCalledWith(
+ userDataMock._id,
+ {
+ password: '12345qwertY',
+ currentPassword: '12345qwert'
+ }
+ )
+ })
+ })
+
+ it('should not save data after negative response', async () => {
+ mockAxiosClient
+ .onPatch(`${URLs.auth.changePassword}/${userDataMock._id}`)
+ .reply(400, {
+ message: 'new password cannot be the same as the current one'
+ })
+
+ const currentPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.currentPassword/i
+ )
+ const passwordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.newPassword/i
+ )
+ const confirmPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.retypePassword/i
+ )
+ const saveButton = screen.getByText(
+ /editProfilePage.profile.passwordSecurityTab.savePassword/i
+ )
+
+ fireEvent.change(currentPasswordInput, {
+ target: { value: '12345qwertY' }
+ })
+ fireEvent.change(passwordInput, {
+ target: { value: '12345qwertY' }
+ })
+ fireEvent.change(confirmPasswordInput, {
+ target: { value: '12345qwertY' }
+ })
+
+ await waitFor(() => {
+ fireEvent.click(saveButton)
+ })
+
+ expect(handleSubmit).not.toHaveBeenCalled()
+ })
+
+ it('should not save empty fields', () => {
+ const currentPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.currentPassword/i
+ )
+ const passwordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.newPassword/i
+ )
+ const confirmPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.retypePassword/i
+ )
+ const saveButton = screen.getByText(
+ /editProfilePage.profile.passwordSecurityTab.savePassword/i
+ )
+
+ fireEvent.change(currentPasswordInput, {
+ target: { value: '' }
+ })
+ fireEvent.change(passwordInput, {
+ target: { value: '' }
+ })
+ fireEvent.change(confirmPasswordInput, {
+ target: { value: '' }
+ })
+
+ fireEvent.click(saveButton)
+
+ expect(handleSubmit).not.toHaveBeenCalled()
+ expect(currentPasswordInput).toHaveValue('')
+ expect(passwordInput).toHaveValue('')
+ expect(confirmPasswordInput).toHaveValue('')
+ })
+
+ it('should show visibility icon', async () => {
+ const visibilityOffIcons = screen.getAllByTestId('VisibilityOffIcon')
+ const visibilityOffIcon = visibilityOffIcons[0]
+ fireEvent.click(visibilityOffIcon)
+
+ const visibilityIcons = screen.getAllByTestId('VisibilityIcon')
+ const visibilityIcon = visibilityIcons[0]
+ await waitFor(() => {
+ expect(visibilityIcon).toBeInTheDocument()
+ expect(visibilityOffIcon).not.toBeInTheDocument()
+ })
+ })
+
+ it('resets form when discard button is clicked', () => {
+ const currentPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.currentPassword/i
+ )
+ const passwordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.newPassword/i
+ )
+ const confirmPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.retypePassword/i
+ )
+ const discardButton = screen.getByText('common.cancel')
+
+ fireEvent.change(passwordInput, { target: { value: 'oldPassword' } })
+ fireEvent.click(discardButton)
+
+ expect(currentPasswordInput).toHaveValue('')
+ expect(passwordInput).toHaveValue('')
+ expect(confirmPasswordInput).toHaveValue('')
+ })
+
+ it('updates state when form fields are changed', () => {
+ const currentPasswordInput = screen.getByLabelText(
+ /editProfilePage.profile.passwordSecurityTab.currentPassword/i
+ )
+ fireEvent.change(currentPasswordInput, { target: { value: 'oldPassword' } })
+ expect(currentPasswordInput).toHaveValue('oldPassword')
+ })
+})
diff --git a/tests/unit/containers/edit-profile/password-security-tab/PasswordSecurityTab.spec.jsx b/tests/unit/containers/edit-profile/password-security-tab/PasswordSecurityTab.spec.jsx
index 832d4e5e0..db441a7e9 100644
--- a/tests/unit/containers/edit-profile/password-security-tab/PasswordSecurityTab.spec.jsx
+++ b/tests/unit/containers/edit-profile/password-security-tab/PasswordSecurityTab.spec.jsx
@@ -2,18 +2,10 @@ import { vi } from 'vitest'
import {
screen,
fireEvent,
- waitFor,
waitForElementToBeRemoved
} from '@testing-library/react'
-import {
- renderWithProviders,
- mockAxiosClient,
- TestSnackbar
-} from '~tests/test-utils'
+import { renderWithProviders, TestSnackbar } from '~tests/test-utils'
import PasswordSecurityTab from '~/containers/edit-profile/password-security-tab/PasswordSecurityTab'
-import { AuthService } from '~/services/auth-service'
-
-import { URLs } from '~/constants/request'
const userDataMock = {
_id: 123456
@@ -25,34 +17,6 @@ vi.mock('~/services/auth-service', () => ({
}
}))
-const handleSubmit = vi.fn()
-
-const changeInputValue = (label, value) => {
- fireEvent.change(label, { target: { value } })
-}
-
-const setupChangePasswordFields = () => {
- const currentPasswordInput = screen.getByLabelText(
- /editProfilePage.profile.passwordSecurityTab.currentPassword/i
- )
- const passwordInput = screen.getByLabelText(
- /editProfilePage.profile.passwordSecurityTab.newPassword/i
- )
- const confirmPasswordInput = screen.getByLabelText(
- /editProfilePage.profile.passwordSecurityTab.retypePassword/i
- )
- const saveButton = screen.getByText(
- /editProfilePage.profile.passwordSecurityTab.savePassword/i
- )
-
- return {
- currentPasswordInput,
- passwordInput,
- confirmPasswordInput,
- saveButton
- }
-}
-
const renderWithMockData = () => {
renderWithProviders(
@@ -74,148 +38,18 @@ describe('PasswordSecurityTab', () => {
renderWithMockData()
})
- it('should save data after positive response', async () => {
- mockAxiosClient
- .onPatch(`${URLs.auth.changePassword}/${userDataMock}`)
- .reply(200)
-
- const {
- currentPasswordInput,
- passwordInput,
- confirmPasswordInput,
- saveButton
- } = setupChangePasswordFields()
-
- fireEvent.change(currentPasswordInput, {
- target: { value: '12345qwert' }
- })
- fireEvent.change(passwordInput, {
- target: { value: '12345qwertY' }
- })
- fireEvent.change(confirmPasswordInput, {
- target: { value: '12345qwertY' }
- })
-
- await waitFor(() => {
- fireEvent.click(saveButton)
- })
-
- const confirmButton = screen.getByText('common.yes')
- fireEvent.click(confirmButton)
-
- await waitFor(() => {
- expect(AuthService.changePassword).toHaveBeenCalledWith(
- userDataMock._id,
- {
- password: '12345qwertY',
- currentPassword: '12345qwert'
- }
- )
- })
- })
-
- it('should not save data after negative response', async () => {
- mockAxiosClient
- .onPatch(`${URLs.auth.changePassword}/${userDataMock}`)
- .reply(400, {
- message: 'new password cannot be the same as the current one'
- })
-
- const {
- currentPasswordInput,
- passwordInput,
- confirmPasswordInput,
- saveButton
- } = setupChangePasswordFields()
-
- fireEvent.change(currentPasswordInput, {
- target: { value: '12345qwertY' }
- })
- fireEvent.change(passwordInput, {
- target: { value: '12345qwertY' }
- })
- fireEvent.change(confirmPasswordInput, {
- target: { value: '12345qwertY' }
- })
-
- await waitFor(() => {
- fireEvent.click(saveButton)
- })
- expect(handleSubmit).not.toHaveBeenCalled()
- })
-
- it('should do not save empty fields', async () => {
- const {
- currentPasswordInput,
- passwordInput,
- confirmPasswordInput,
- saveButton
- } = setupChangePasswordFields()
-
- fireEvent.change(currentPasswordInput, {
- target: { value: '' }
- })
- fireEvent.change(passwordInput, {
- target: { value: '' }
- })
- fireEvent.change(confirmPasswordInput, {
- target: { value: '' }
- })
-
- fireEvent.click(saveButton)
-
- expect(handleSubmit).not.toHaveBeenCalled()
-
- expect(currentPasswordInput).toHaveValue('')
- expect(passwordInput).toHaveValue('')
- expect(confirmPasswordInput).toHaveValue('')
- })
-
- it('should show visibility icon', async () => {
- const visibilityOffIcons = screen.getAllByTestId('VisibilityOffIcon')
- const visibilityOffIcon = visibilityOffIcons[0]
- fireEvent.click(visibilityOffIcon)
-
- const visibilityIcons = screen.getAllByTestId('VisibilityIcon')
- const visibilityIcon = visibilityIcons[0]
- await waitFor(() => {
- expect(visibilityIcon).toBeInTheDocument()
- expect(visibilityOffIcon).not.toBeInTheDocument()
- })
- })
-
it('renders title and description', () => {
const title = screen.getByText(
'editProfilePage.profile.passwordSecurityTab.title'
)
const description = screen.getByText(
- 'editProfilePage.profile.passwordSecurityTab.description'
+ 'editProfilePage.profile.passwordSecurityTab.subTitle'
)
expect(title).toBeInTheDocument()
expect(description).toBeInTheDocument()
})
- it('resets form when discard button is clicked', () => {
- const { currentPasswordInput } = setupChangePasswordFields()
-
- const discardButtonText = screen.getByText('common.discard')
-
- changeInputValue(currentPasswordInput, 'oldPassword')
-
- fireEvent.click(discardButtonText)
-
- expect(currentPasswordInput).toHaveValue('')
- })
-
- it('updates state when form fields are changed', () => {
- const { currentPasswordInput } = setupChangePasswordFields()
-
- changeInputValue(currentPasswordInput, 'oldPassword')
-
- expect(currentPasswordInput).toHaveValue('oldPassword')
- })
-
- it('checks is ConfirmDialog open when deactivate account button is clicked', () => {
+ it('checks if ConfirmDialog is open when deactivate account button is clicked', () => {
const deactivateAccountButton = screen.getByText(
'editProfilePage.profile.passwordSecurityTab.deactivateAccount'
)
@@ -228,7 +62,7 @@ describe('PasswordSecurityTab', () => {
expect(deactivateTitle).toBeInTheDocument()
})
- it('checks is ConfirmDialog closed when cancel button is clicked', async () => {
+ it('checks if ConfirmDialog is closed when cancel button is clicked', async () => {
const deactivateAccountButton = screen.getByText(
'editProfilePage.profile.passwordSecurityTab.deactivateAccount'
)