diff --git a/hotel-management/src/App.tsx b/hotel-management/src/App.tsx index 618c22d..7f685f7 100644 --- a/hotel-management/src/App.tsx +++ b/hotel-management/src/App.tsx @@ -16,10 +16,10 @@ import Room from './pages/Room'; import NotFound from './pages/NotFound'; import Login from '@src/pages/Login'; import Account from '@src/pages/Account'; +import SignUpAccount from '@src/pages/SignUpAccount'; // Constants import * as PATH from './constants/path'; -import SignUpAccount from "@src/pages/SignUpAccount"; const queryClient = new QueryClient(); @@ -42,7 +42,10 @@ function App() { } /> } /> } /> - } /> + } + /> } /> } /> diff --git a/hotel-management/src/hooks/authentication/useSignUpAccount.ts b/hotel-management/src/hooks/authentication/useSignUpAccount.ts new file mode 100644 index 0000000..24e37ae --- /dev/null +++ b/hotel-management/src/hooks/authentication/useSignUpAccount.ts @@ -0,0 +1,17 @@ +import { useMutation } from '@tanstack/react-query'; +import { createAccount as createAccountFn } from '@src/services/authenticationService.ts'; +import toast from 'react-hot-toast'; + +const useSignUpAccount = () => { + const { mutate: createAccount, isPending: isCreating } = useMutation({ + mutationFn: createAccountFn, + onSuccess: (account) => { + toast.success(`Create user ${account!.user!.email} successful!`); + }, + onError: (err) => toast.error(err.message), + }); + + return { createAccount, isCreating }; +}; + +export { useSignUpAccount }; diff --git a/hotel-management/src/pages/SignUpAccount/SignUpForm.tsx b/hotel-management/src/pages/SignUpAccount/SignUpForm.tsx new file mode 100644 index 0000000..c9e9d45 --- /dev/null +++ b/hotel-management/src/pages/SignUpAccount/SignUpForm.tsx @@ -0,0 +1,107 @@ +import { useForm } from 'react-hook-form'; +import Form from '@src/components/Form'; +import Input from '@src/commons/styles/Input.ts'; +import { isValidRegex, isValidString } from '@src/helpers/validators.ts'; +import { REGEX } from '@src/constants/commons.ts'; +import { + INVALID_EMAIL, + INVALID_STRING, + PASSWORD_CONDITION, + PASSWORD_NOT_MATCH, + PASSWORD_NOT_MATCH_REQUIREMENT, + REQUIRED_FIELD_ERROR, +} from '@src/constants/formValidateMessage.ts'; +import { useEffect } from 'react'; +import toast from 'react-hot-toast'; +import { useSignUpAccount } from '@src/hooks/authentication/useSignUpAccount.ts'; + +interface ISignUpAccountForm { + email: string; + fullName: string; + password: string; + confirmPassword: string; +} + +const SignUpAccountForm = () => { + const { createAccount, isCreating } = useSignUpAccount(); + const { + register, + handleSubmit, + formState: { errors }, + getValues, + reset, + } = useForm(); + + useEffect(() => { + if (errors?.password?.message) { + toast.error(PASSWORD_CONDITION); + } + }, [errors?.password?.message]); + + const onSubmit = (data: ISignUpAccountForm) => { + createAccount({ email: data.email, password: data.password }); + + reset(); + }; + + return ( +
+ + + isValidRegex(REGEX.EMAIL, value) || INVALID_EMAIL, + })} + /> + + + + isValidString(value) || INVALID_STRING, + })} + /> + + + + + isValidRegex(REGEX.PASSWORD, v) || + PASSWORD_NOT_MATCH_REQUIREMENT, + }, + })} + /> + + + + + getValues().password === value || PASSWORD_NOT_MATCH, + })} + /> + + + + + Create Account + + +
+ ); +}; + +export default SignUpAccountForm; diff --git a/hotel-management/src/pages/SignUpAccount/index.tsx b/hotel-management/src/pages/SignUpAccount/index.tsx new file mode 100644 index 0000000..7eb96e9 --- /dev/null +++ b/hotel-management/src/pages/SignUpAccount/index.tsx @@ -0,0 +1,18 @@ +import {FormArea, StyledSignUpAccount, Title} from "@src/pages/SignUpAccount/styled.ts"; +import SignUpForm from "@src/pages/SignUpAccount/SignUpForm.tsx"; + + +const SignUpAccount = () => { + return ( + + Create account + + + + + + + ); +} + +export default SignUpAccount; diff --git a/hotel-management/src/pages/SignUpAccount/styled.ts b/hotel-management/src/pages/SignUpAccount/styled.ts new file mode 100644 index 0000000..b70e8d6 --- /dev/null +++ b/hotel-management/src/pages/SignUpAccount/styled.ts @@ -0,0 +1,31 @@ +import styled from 'styled-components'; + +const Title = styled.h2` + font-size: var(--fs-md); + color: var(--dark-text); + text-transform: capitalize; +`; + +const StyledSignUpAccount = styled.div` + padding: 20px; + + display: flex; + flex-direction: column; + align-items: center; +`; + +const FormArea = styled.div` + border-radius: var(--radius-sm); + border: 1px solid var(--border-color); + + padding: 20px 40px; + width: 500px; + + margin-top: 50px; +` + +export { + Title, + StyledSignUpAccount, + FormArea, +};