From 5c91bddfe7e91dfa3114ba175621b8b18289fa74 Mon Sep 17 00:00:00 2001 From: Maksim Eltyshev Date: Fri, 26 Aug 2022 18:59:44 +0200 Subject: [PATCH] feat: Stronger password policy --- .../UserPasswordEditStep.jsx | 23 +++++++++++-------- .../UserPasswordEditStep.module.scss | 6 +++++ client/src/locales/en/core.js | 2 ++ client/src/locales/ru/core.js | 2 ++ client/src/utils/validator.js | 6 ++++- server/api/controllers/users/create.js | 2 ++ .../api/controllers/users/update-password.js | 2 ++ 7 files changed, 33 insertions(+), 10 deletions(-) diff --git a/client/src/components/UserPasswordEditStep/UserPasswordEditStep.jsx b/client/src/components/UserPasswordEditStep/UserPasswordEditStep.jsx index c8be8f65..f809c686 100644 --- a/client/src/components/UserPasswordEditStep/UserPasswordEditStep.jsx +++ b/client/src/components/UserPasswordEditStep/UserPasswordEditStep.jsx @@ -7,6 +7,7 @@ import { useDidUpdate, usePrevious, useToggle } from '../../lib/hooks'; import { Input, Popup } from '../../lib/custom-ui'; import { useForm } from '../../hooks'; +import { isPassword } from '../../utils/validator'; import styles from './UserPasswordEditStep.module.scss'; @@ -56,7 +57,7 @@ const UserPasswordEditStep = React.memo( const currentPasswordField = useRef(null); const handleSubmit = useCallback(() => { - if (!data.password) { + if (!data.password || !isPassword(data.password)) { passwordField.current.select(); return; } @@ -112,14 +113,18 @@ const UserPasswordEditStep = React.memo( )}
{t('common.newPassword')}
- +
+ +
+ {t('common.mustBeAtLeast6CharactersLongAndContainAtLeastOneLetterAndNumber')} +
+
{usePasswordConfirmation && ( <>
{t('common.currentPassword')}
diff --git a/client/src/components/UserPasswordEditStep/UserPasswordEditStep.module.scss b/client/src/components/UserPasswordEditStep/UserPasswordEditStep.module.scss index 8246167c..6f5b7c02 100644 --- a/client/src/components/UserPasswordEditStep/UserPasswordEditStep.module.scss +++ b/client/src/components/UserPasswordEditStep/UserPasswordEditStep.module.scss @@ -3,6 +3,12 @@ margin-bottom: 8px; } + .note { + font-size: 11px; + margin-top: 4px; + opacity: 0.5; + } + .text { color: #444444; font-size: 12px; diff --git a/client/src/locales/en/core.js b/client/src/locales/en/core.js index 3c18c09c..2333b964 100644 --- a/client/src/locales/en/core.js +++ b/client/src/locales/en/core.js @@ -105,6 +105,8 @@ export default { members: 'Members', minutes: 'Minutes', moveCard_title: 'Move Card', + mustBeAtLeast6CharactersLongAndContainAtLeastOneLetterAndNumber: + 'Must be at least 6 characters long and contain at least one letter and number', name: 'Name', newEmail: 'New e-mail', newPassword: 'New password', diff --git a/client/src/locales/ru/core.js b/client/src/locales/ru/core.js index 251da210..702345d1 100644 --- a/client/src/locales/ru/core.js +++ b/client/src/locales/ru/core.js @@ -100,6 +100,8 @@ export default { members: 'Участники', minutes: 'Минуты', moveCard: 'Перемещение карточки', + mustBeAtLeast6CharactersLongAndContainAtLeastOneLetterAndNumber: + 'Должен быть не менее 6 символов и содержать хотя бы одну букву и цифру', name: 'Имя', newEmail: 'Новый e-mail', newPassword: 'Новый пароль', diff --git a/client/src/utils/validator.js b/client/src/utils/validator.js index 75f8f41d..87efc99b 100644 --- a/client/src/utils/validator.js +++ b/client/src/utils/validator.js @@ -1,6 +1,10 @@ +const PASSWORD_REGEX = /^(?=.*[A-Za-z])(?=.*\d).+$/; const USERNAME_REGEX = /^[a-zA-Z0-9]+((_|\.)?[a-zA-Z0-9])*$/; -// eslint-disable-next-line import/prefer-default-export +export const isPassword = (string) => { + return string.length >= 3 && PASSWORD_REGEX.test(string); +}; + export const isUsername = (string) => { return string.length >= 3 && string.length <= 16 && USERNAME_REGEX.test(string); }; diff --git a/server/api/controllers/users/create.js b/server/api/controllers/users/create.js index e0dd6dfe..9b397a1c 100755 --- a/server/api/controllers/users/create.js +++ b/server/api/controllers/users/create.js @@ -16,6 +16,8 @@ module.exports = { }, password: { type: 'string', + minLength: 6, + regex: /^(?=.*[A-Za-z])(?=.*\d).+$/, required: true, }, name: { diff --git a/server/api/controllers/users/update-password.js b/server/api/controllers/users/update-password.js index aac537b8..0ea1afad 100644 --- a/server/api/controllers/users/update-password.js +++ b/server/api/controllers/users/update-password.js @@ -18,6 +18,8 @@ module.exports = { }, password: { type: 'string', + minLength: 6, + regex: /^(?=.*[A-Za-z])(?=.*\d).+$/, required: true, }, currentPassword: {