-
Notifications
You must be signed in to change notification settings - Fork 6
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
29 changed files
with
347 additions
and
316 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
6 changes: 6 additions & 0 deletions
6
web-app/client/src/components/Inputs/Password/Password.module.scss
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
.tooltip { | ||
ul { | ||
list-style: disc; | ||
margin-left: 24px; | ||
} | ||
} |
52 changes: 52 additions & 0 deletions
52
web-app/client/src/components/Inputs/Password/Password.test.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,52 @@ | ||
import { render, screen } from '@testing-library/react'; | ||
import userEvent from '@testing-library/user-event'; | ||
|
||
import { TestPassword } from './TestPassword'; | ||
|
||
const user = userEvent.setup(); | ||
|
||
describe('Variants for password', () => { | ||
beforeEach(() => { | ||
jest.clearAllMocks(); | ||
}); | ||
|
||
const typePassword = async (text: string) => { | ||
render(<TestPassword />); | ||
const errorMessage = | ||
'The password does not match the pattern (see tooltip)'; | ||
const input = screen.getByPlaceholderText('admin1234'); | ||
const trigger = screen.getByRole('submit'); | ||
await user.type(input, text); | ||
await user.click(trigger); | ||
return screen.queryByText(errorMessage); | ||
}; | ||
test('Should show error cause too shot password', async () => { | ||
const error = await typePassword('Aa23.0'); | ||
expect(error).toBeTruthy(); | ||
}); | ||
|
||
test('Should show error cause password without digit', async () => { | ||
const error = await typePassword('Aaaaaa.a'); | ||
expect(error).toBeTruthy(); | ||
}); | ||
|
||
test('Should show error cause password without special symbol', async () => { | ||
const error = await typePassword('Aaaa2312'); | ||
expect(error).toBeTruthy(); | ||
}); | ||
|
||
test('Should show error cause password without uppercase letter', async () => { | ||
const error = await typePassword('aaaa23.0'); | ||
expect(error).toBeTruthy(); | ||
}); | ||
|
||
test('Should show error cause password without lowercase letter', async () => { | ||
const error = await typePassword('AAAA23.0'); | ||
expect(error).toBeTruthy(); | ||
}); | ||
|
||
test('Should not show error cause good password', async () => { | ||
const error = await typePassword('Aaaa23.0'); | ||
expect(error).toBeNull(); | ||
}); | ||
}); |
86 changes: 86 additions & 0 deletions
86
web-app/client/src/components/Inputs/Password/Password.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,86 @@ | ||
import { ComponentProps, FC } from 'react'; | ||
import { Text } from '@components/Inputs'; | ||
import styles from './Password.module.scss'; | ||
import { Control, Controller, FieldValues, Path } from 'react-hook-form'; | ||
import isStrongPassword from 'validator/lib/isStrongPassword'; | ||
|
||
const passwordTooltip = ( | ||
<div className={styles.tooltip}> | ||
The password must contain | ||
<ul> | ||
<li>at least 8 characters</li> | ||
<li>at least 1 uppercase letter</li> | ||
<li>at least 1 lowercase letter</li> | ||
<li>at least 1 digit</li> | ||
<li>at least 1 special character</li> | ||
</ul> | ||
</div> | ||
); | ||
|
||
const customValidateFunction = (value: string) => { | ||
return ( | ||
isStrongPassword(value) || | ||
'The password does not match the pattern (see tooltip)' | ||
); | ||
}; | ||
|
||
type ControlRules<T extends FieldValues> = ComponentProps< | ||
typeof Controller<T> | ||
>['rules']; | ||
|
||
type TextProps = ComponentProps<typeof Text>; | ||
|
||
type ControlProps<T extends FieldValues> = { | ||
controlName: Path<T>; | ||
control: Control<T>; | ||
rules?: ControlRules<T>; | ||
}; | ||
|
||
type PasswordProps<T extends FieldValues> = TextProps & | ||
ControlProps<T> & { | ||
needStrengthValidation?: boolean; | ||
}; | ||
|
||
const Password = <T extends FieldValues>({ | ||
controlName, | ||
control, | ||
rules, | ||
needStrengthValidation = true, | ||
...rest | ||
}: PasswordProps<T>) => { | ||
let validate; | ||
if (!needStrengthValidation) validate = rules?.validate; | ||
else if (typeof rules?.validate === 'object') | ||
validate = { | ||
...rules.validate, | ||
strongPassword: customValidateFunction, | ||
}; | ||
else if (typeof rules?.validate === 'function') | ||
validate = { | ||
validation: rules?.validate, | ||
strongPassword: customValidateFunction, | ||
}; | ||
else if (rules?.validate === undefined) validate = customValidateFunction; | ||
|
||
return ( | ||
<Controller | ||
name={controlName} | ||
control={control} | ||
rules={{ | ||
...rules, | ||
validate: validate as any, | ||
}} | ||
render={({ field, fieldState }) => ( | ||
<Text | ||
type="password" | ||
tooltip={passwordTooltip} | ||
{...field} | ||
error={fieldState.error?.message} | ||
{...rest} | ||
/> | ||
)} | ||
/> | ||
); | ||
}; | ||
|
||
export default Password; |
49 changes: 49 additions & 0 deletions
49
web-app/client/src/components/Inputs/Password/TestPassword.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
import { FC } from 'react'; | ||
import { useForm } from 'react-hook-form'; | ||
import Button from '@components/Button'; | ||
import Password from './Password'; | ||
|
||
type Inputs = { | ||
password: string; | ||
}; | ||
|
||
const defaultValues: Inputs = { | ||
password: '', | ||
}; | ||
|
||
export const TestPassword: FC = () => { | ||
|
||
const { | ||
control, | ||
handleSubmit, | ||
formState: { errors, isSubmitting }, | ||
} = useForm<Inputs>({ | ||
defaultValues, | ||
}); | ||
|
||
const onSubmit = handleSubmit(async () => { | ||
console.log('submit') | ||
}); | ||
|
||
return ( | ||
<> | ||
<form onSubmit={onSubmit}> | ||
<Password | ||
control={control} | ||
controlName="password" | ||
label="Password" | ||
placeholder="admin1234" | ||
rules={{ required: 'Required' }} | ||
/> | ||
<Button | ||
variant="primary" | ||
type="submit" | ||
disabled={isSubmitting} | ||
role="submit" | ||
> | ||
Test Button | ||
</Button> | ||
</form> | ||
</> | ||
); | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
export { default } from './Password'; |
Oops, something went wrong.