Reset Page Completed

This commit is contained in:
Ebube
2023-05-05 01:21:55 +01:00
parent 12e940d9b3
commit dd94177a95
5 changed files with 230 additions and 131 deletions
+64 -38
View File
@@ -4,17 +4,16 @@ import { toast } from "react-toastify";
import googleLogo from "../../../assets/images/google-logo.svg"; import googleLogo from "../../../assets/images/google-logo.svg";
import appleLogo from "../../../assets/images/apple-black.svg"; import appleLogo from "../../../assets/images/apple-black.svg";
import facebookLogo from "../../../assets/images/facebook-4.svg"; import facebookLogo from "../../../assets/images/facebook-4.svg";
import WrenchBoard from "../../../assets/images/wrenchboard.png" import WrenchBoard from "../../../assets/images/wrenchboard.png";
import usersService from "../../../services/UsersService"; import usersService from "../../../services/UsersService";
import InputCom from "../../Helpers/Inputs/InputCom"; import InputCom from "../../Helpers/Inputs/InputCom";
import AuthLayout from "../AuthLayout"; import AuthLayout from "../AuthLayout";
import { useDispatch, useSelector } from "react-redux"; import { useDispatch, useSelector } from "react-redux";
import {updateUserDetails} from '../../../store/UserDetails' import { updateUserDetails } from "../../../store/UserDetails";
export default function Login() { export default function Login() {
const dispatch = useDispatch();
const dispatch = useDispatch()
const [checked, setValue] = useState(false); const [checked, setValue] = useState(false);
const [loginLoading, setLoginLoading] = useState(false); const [loginLoading, setLoginLoading] = useState(false);
@@ -22,7 +21,7 @@ export default function Login() {
//login error state //login error state
const [loginError, setLoginError] = useState(false); const [loginError, setLoginError] = useState(false);
// for the catch error // for the catch error
const [msgError, setMsgError] = useState(''); const [msgError, setMsgError] = useState("");
const rememberMe = () => { const rememberMe = () => {
setValue(!checked); setValue(!checked);
@@ -41,57 +40,62 @@ export default function Login() {
const navigate = useNavigate(); const navigate = useNavigate();
const userApi = new usersService(); const userApi = new usersService();
const doLogin = async () => { const doLogin = async () => {
if (email == '' && password == '') {
setMsgError('Please fill in fields')
}
try { try {
if (email !== "" && password !== "") { if (email !== "" && password !== "") {
var postData = { var postData = {
username: email, username: email,
password: password, password: password,
sessionid: 'STARTING' sessionid: "STARTING",
}; };
const loginResult = await userApi.logInUser(postData); // just for a test const loginResult = await userApi.logInUser(postData); // just for a test
//debugger; //debugger;
// if (email === "support@mermsemr.com") { // if (email === "support@mermsemr.com") {
if (loginResult.data.status > 0 && loginResult.data.internal_return == 100 && loginResult.data.session != '') { // just for a start if (
loginResult.data.status > 0 &&
loginResult.data.internal_return == 100 &&
loginResult.data.session != ""
) {
// just for a start
localStorage.setItem("member_id", `${loginResult.data.member_id}`); localStorage.setItem("member_id", `${loginResult.data.member_id}`);
localStorage.setItem("uid", `${loginResult.data.uid}`); localStorage.setItem("uid", `${loginResult.data.uid}`);
localStorage.setItem("session_token", `${loginResult.data.session}`); localStorage.setItem("session_token", `${loginResult.data.session}`);
localStorage.setItem("session", `${loginResult.data.session}`); localStorage.setItem("session", `${loginResult.data.session}`);
setLoginLoading(true); setLoginLoading(true);
// userApi.getUserReminders(); //testing // userApi.getUserReminders(); //testing
dispatch(updateUserDetails(loginResult.data)) dispatch(updateUserDetails(loginResult.data));
setTimeout(() => { setTimeout(() => {
navigate("/", { replace: true }); navigate("/", { replace: true });
setLoginLoading(false); setLoginLoading(false);
}, 2000); }, 2000);
} else { } else {
// toast.error("Invalid Credential"); // toast.error("Invalid Credential");
setLoginError(true) setLoginError(true);
} }
} else {
setMsgError("Please fill in fields");
} }
} catch (error) { } catch (error) {
setMsgError('An error occurred') setMsgError("An error occurred");
} finally { } finally {
setTimeout(() => { setTimeout(() => {
setLoginError(false) setLoginError(false);
setMsgError(null) setMsgError(null);
}, Number(process.env.REACT_APP_LOGIN_ERROR_TIMEOUT)) }, Number(process.env.REACT_APP_LOGIN_ERROR_TIMEOUT));
} }
}; };
return ( return (
<> <>
<AuthLayout <AuthLayout slogan="Welcome to WrenchBoard">
slogan="Welcome to WrenchBoard"
>
<div className="w-full"> <div className="w-full">
<div className='mb-12'> <div className="mb-12">
<Link to='#'> <Link to="#">
<img src={WrenchBoard} alt="wrenchboard" className="h-10 mx-auto" /> <img
src={WrenchBoard}
alt="wrenchboard"
className="h-10 mx-auto"
/>
</Link> </Link>
</div> </div>
<div className="content-wrapper login shadow-md w-full lg:max-w-[500px] mx-auto flex justify-center items-center xl:bg-white dark:bg-dark-white 2xl:w-[828px] rounded-[0.475rem] sm:p-7 p-5"> <div className="content-wrapper login shadow-md w-full lg:max-w-[500px] mx-auto flex justify-center items-center xl:bg-white dark:bg-dark-white 2xl:w-[828px] rounded-[0.475rem] sm:p-7 p-5">
@@ -100,7 +104,15 @@ export default function Login() {
<h1 className="text-[#181c32] font-semibold dark:text-white mb-3 leading-[27.3px] text-[22.75px]"> <h1 className="text-[#181c32] font-semibold dark:text-white mb-3 leading-[27.3px] text-[22.75px]">
Sign In to WrenchBoard Sign In to WrenchBoard
</h1> </h1>
<span className="text-gray-400 font-medium text-[16.25px] leading-[24.375px]">New Here? <Link to='/signup' className='font-semibold text-[#4687ba] hover:text-[#009ef7] transition'>Create an Account</Link></span> <span className="text-gray-400 font-medium text-[16.25px] leading-[24.375px]">
New Here?{" "}
<Link
to="/signup"
className="font-semibold text-[#4687ba] hover:text-[#009ef7] transition"
>
Create an Account
</Link>
</span>
</div> </div>
<div className="input-area"> <div className="input-area">
<div className="input-item mb-5"> <div className="input-item mb-5">
@@ -160,8 +172,23 @@ export default function Login() {
Forgot Password Forgot Password
</a> </a>
</div> */} </div> */}
{loginError && <div className="relative p-4 text-[#912741] bg-[#fcd9e2] border-[#fbc6d3] mb-4 rounded-[0.475rem] text-md font-thin leading-[19.5px] text-[13px]">Invalid username or password- Please <Link to='/#' className='text-[#009ef7]'>reset your password</Link> or <Link to='/signup' className='text-[#009ef7]'>create a new account</Link></div>} {loginError && (
{msgError && <div className="relative p-4 text-[#912741] bg-[#fcd9e2] border-[#fbc6d3] mb-4 rounded-[0.475rem] text-md font-light leading-[19.5px] text-[13px]">{msgError}</div>} <div className="relative p-4 text-[#912741] bg-[#fcd9e2] border-[#fbc6d3] mb-4 rounded-[0.475rem] text-md font-thin leading-[19.5px] text-[13px]">
Invalid username or password- Please{" "}
<Link to="/#" className="text-[#009ef7]">
reset your password
</Link>{" "}
or{" "}
<Link to="/signup" className="text-[#009ef7]">
create a new account
</Link>
</div>
)}
{msgError && (
<div className="relative p-4 text-[#912741] bg-[#fcd9e2] border-[#fbc6d3] mb-4 rounded-[0.475rem] text-md font-light leading-[19.5px] text-[13px]">
{msgError}
</div>
)}
<div className="signin-area mb-3.5"> <div className="signin-area mb-3.5">
<div className="flex justify-center"> <div className="flex justify-center">
<button <button
@@ -176,9 +203,9 @@ export default function Login() {
)} )}
</button> </button>
</div> </div>
<BrandBtn link='#' imgSrc={googleLogo} brand='Google' /> <BrandBtn link="#" imgSrc={googleLogo} brand="Google" />
<BrandBtn link='#' imgSrc={facebookLogo} brand='Facebook' /> <BrandBtn link="#" imgSrc={facebookLogo} brand="Facebook" />
<BrandBtn link='#' imgSrc={appleLogo} brand='Apple' /> <BrandBtn link="#" imgSrc={appleLogo} brand="Apple" />
</div> </div>
{/* <div className="signup-area flex justify-center"> {/* <div className="signup-area flex justify-center">
<p className="sm:text-lg text-sm text-thin-light-gray font-normal"> <p className="sm:text-lg text-sm text-thin-light-gray font-normal">
@@ -188,7 +215,10 @@ export default function Login() {
</a> </a>
</p> </p>
</div> */} </div> */}
<div className="pt-5 text-[#181c32] text-center font-semibold text-[13.975px] leading-[20.9625px]">This site is protected by hCaptcha and the our Privacy Policy and Terms of Service apply.</div> <div className="pt-5 text-[#181c32] text-center font-semibold text-[13.975px] leading-[20.9625px]">
This site is protected by hCaptcha and the our Privacy Policy
and Terms of Service apply.
</div>
</div> </div>
</div> </div>
</div> </div>
@@ -198,11 +228,7 @@ export default function Login() {
); );
} }
const BrandBtn = ({ const BrandBtn = ({ link, imgSrc, brand }) => {
link,
imgSrc,
brand
}) => {
return ( return (
<div className="flex justify-center bottomMargin"> <div className="flex justify-center bottomMargin">
<a <a
@@ -215,5 +241,5 @@ const BrandBtn = ({
</span> </span>
</a> </a>
</div> </div>
) );
} };
+33 -26
View File
@@ -56,17 +56,13 @@ export default function SignUp() {
const handleSignUp = async () => { const handleSignUp = async () => {
let { country, first_name, last_name, email, password } = formData; let { country, first_name, last_name, email, password } = formData;
if (email === "" && password === "" && first_name === "") {
setMsgError("Please fill in fields");
}
try { try {
if ( if (
email !== "" && email !== "" &&
password !== "" && password !== "" &&
first_name !== "" && first_name !== "" &&
last_name !== "" last_name !== "" &&
country !== ""
) { ) {
setSignUpLoading(true); setSignUpLoading(true);
const reqData = { const reqData = {
@@ -98,6 +94,8 @@ export default function SignUp() {
setSignUpLoading(false); setSignUpLoading(false);
setMsgError("An error occurred"); setMsgError("An error occurred");
} }
} else {
setMsgError("Please fill in fields");
} }
} catch (error) { } catch (error) {
throw new Error(error); throw new Error(error);
@@ -262,7 +260,7 @@ export default function SignUp() {
<button <button
type="button" type="button"
onClick={handleSignUp} onClick={handleSignUp}
className={`rounded-[0.475rem] mb-6 text-white flex justify-center bg-[#4687ba] hover:bg-[#009ef7] transition-all duration-300 items-center h-[42px] py-[0.8875rem] px-[1.81rem] text-[14.95px]`} className={`rounded-[0.475rem] mb-6 text-white flex justify-center bg-[#4687ba] hover:bg-[#009ef7] transition-all duration-300 items-center h-[42px] py-[0.8875rem] px-[1.81rem] text-[14.95px] btn-login`}
> >
{signUpLoading ? ( {signUpLoading ? (
<div className="signup btn-loader"></div> <div className="signup btn-loader"></div>
@@ -278,26 +276,35 @@ export default function SignUp() {
</div> </div>
</div> </div>
<div className="flex-1 flex justify-center items-center p-10"> <div className="flex-1 flex justify-center items-center p-10">
<div className="flex items-center"> <div className="flex items-center">
<Link to="#" className="text-[#a1a5b7] text-[15px] px-2 font-medium hover:text-[#009ef7]"> <Link
About to="#"
</Link> className="text-[#a1a5b7] text-[15px] px-2 font-medium hover:text-[#009ef7]"
<Link to="#" className="text-[#a1a5b7] text-[15px] px-2 font-medium hover:text-[#009ef7]"> >
Services About
</Link> </Link>
<Link to="#" className="text-[#a1a5b7] text-[15px] px-2 font-medium hover:text-[#009ef7]"> <Link
Contact Us to="#"
</Link> className="text-[#a1a5b7] text-[15px] px-2 font-medium hover:text-[#009ef7]"
>
Services
</Link>
<Link
to="#"
className="text-[#a1a5b7] text-[15px] px-2 font-medium hover:text-[#009ef7]"
>
Contact Us
</Link>
</div>
</div>
<div className="flex-1 flex justify-center items-center p-10">
<p className="text-black text-[15px] px-2 font-medium flex items-center">
<span className="text-3xl mt-2 mr-1">©</span> 2023 -{" "}
<Link to="/" className="text-[#009ef7] ml-1">
WrenchBoard
</Link>{" "}
</p>
</div> </div>
</div>
<div className="flex-1 flex justify-center items-center p-10">
<p className="text-black text-[15px] px-2 font-medium flex items-center">
<span className="text-3xl mt-2 mr-1">©</span> 2023 - {" "}
<Link to="/" className="text-[#009ef7] ml-1">
WrenchBoard
</Link>{" "}
</p>
</div>
</div> </div>
</div> </div>
</div> </div>
@@ -30,10 +30,6 @@ export default function VerifyLink() {
// if verification is okay. set a complete signup form // if verification is okay. set a complete signup form
const completeSignup = async () => { const completeSignup = async () => {
if (email === "" && password === "") {
setMsgError("Please fill in fields");
}
try { try {
if (email !== "" && password !== "") { if (email !== "" && password !== "") {
setLinkLoader(true); setLinkLoader(true);
@@ -45,7 +41,7 @@ export default function VerifyLink() {
verify_link: token, verify_link: token,
action: 11012, action: 11012,
}; };
const res = await userApi.CompleteSignUp(postData); const res = await userApi?.CompleteSignUp(postData);
if (res.status === 200) { if (res.status === 200) {
const { data } = res; const { data } = res;
@@ -67,13 +63,15 @@ export default function VerifyLink() {
} }
} else { } else {
setLinkLoader(false); setLinkLoader(false);
setLinkSuccess(false) setLinkSuccess(false);
setMsgError("An error occurred"); setMsgError("An error occurred");
} }
} else {
setMsgError("Please fill in fields");
} }
} catch (error) { } catch (error) {
setLinkLoader(false); setLinkLoader(false);
setLinkSuccess(false) setLinkSuccess(false);
throw new Error(error); throw new Error(error);
} finally { } finally {
setTimeout(() => { setTimeout(() => {
+125 -57
View File
@@ -7,83 +7,129 @@ import WrenchBoard from "../../../assets/images/wrenchboard.png";
const VerifyPassword = () => { const VerifyPassword = () => {
const [password, setPassword] = useState(""); const [password, setPassword] = useState("");
const [confirmPassword, setConfirmPassword] = useState("");
const [msgError, setMsgError] = useState(""); const [msgError, setMsgError] = useState("");
const [linkLoader, setLinkLoader] = useState(false); const [linkLoader, setLinkLoader] = useState(false);
const [pageLoader, setPageLoader] = useState(true);
const [linkSuccess, setLinkSuccess] = useState(true); const [linkSuccess, setLinkSuccess] = useState(true);
const navigate = useNavigate(); const navigate = useNavigate();
const location = useLocation(); const location = useLocation();
const queryParams = new URLSearchParams(location?.search); const queryParams = new URLSearchParams(location?.search);
const token = queryParams.get("complereset"); const token = queryParams.get("passlink");
const userApi = new usersService(); const userApi = new usersService();
// little checker for the validity of the token
if (token?.length != 64) {
setLinkSuccess(false);
}
// Password // Password
const handlePassword = (e) => { const handlePassword = (e) => {
setPassword(e.target.value); let { name, value } = e?.target;
if (name == "password") setPassword(value);
if (name == "confirm_password") setConfirmPassword(value);
}; };
const completeReset = async () => { const completeReset = async () => {
if (password === "") { try {
if (password !== "" && confirmPassword !== "") {
if (password === confirmPassword) {
setLinkLoader(true);
var reqData = {
sessionid: "DUMMY-CANNOT_BE_EMPTY",
reset_link: token,
newpass: password,
step: 300,
action: 730,
};
const res = await userApi?.CompleteResetPassword(reqData);
if (res.status === 200) {
const { data } = res;
if (data?.status > 0 && data?.email) {
setTimeout(() => {
navigate("/login", { replace: true });
setLinkLoader(false);
}, 2000);
} else {
setLinkLoader(false);
setMsgError("An error occurred");
}
if (data && data?.status == "Invalid Request") {
setLinkLoader(false);
setLinkSuccess(false);
}
} else {
setLinkLoader(false);
setLinkSuccess(false);
}
} else {
setLinkLoader(false);
setMsgError("Passwords does not match");
}
} else {
setMsgError("Please fill in fields"); setMsgError("Please fill in fields");
} }
} catch (error) {
try { setLinkLoader(false);
if(password != ""){ setLinkSuccess(false);
setLinkLoader(true) throw new Error(error);
var reqData = { } finally {
sessionid: 'dummy', setTimeout(() => {
reset_link: token, setMsgError(null);
newpass: password, }, process.env.REACT_APP_SIGNUP_ERROR_TIMEOUT);
step: 300, }
action: 730 };
}
}
} catch (error) {
}
}
return ( return (
<> <>
<AuthLayout slogan="Welcome to WrenchBoard"> <AuthLayout slogan="Welcome to WrenchBoard">
{pageLoader ? ( <div className="w-full">
<img src={WrenchBoard} alt="wrenchboard" className="h-10 mx-auto" /> <div className="mb-12">
) : ( <Link to="#">
<div className="w-full"> <img
<div className="mb-12"> src={WrenchBoard}
<Link to="#"> alt="wrenchboard"
<img className="h-10 mx-auto"
src={WrenchBoard} />
alt="wrenchboard" </Link>
className="h-10 mx-auto" </div>
/> <div className="content-wrapper login shadow-md w-full lg:max-w-[500px] mx-auto flex justify-center items-center dark:bg-dark-white 2xl:w-[828px] rounded-[0.475rem] sm:p-7 p-5">
</Link> <div className="w-full">
</div> <div className="title-area flex flex-col justify-center items-center relative text-center mb-7">
<div className="content-wrapper login shadow-md w-full lg:max-w-[500px] mx-auto flex justify-center items-center dark:bg-dark-white 2xl:w-[828px] rounded-[0.475rem] sm:p-7 p-5"> <h1 className="text-[#181c32] font-semibold dark:text-white mb-3 leading-[27.3px] text-[22.75px]">
<div className="w-full"> {linkSuccess ? "Password Reset" : "Invalid verification link"}
<div className="title-area flex flex-col justify-center items-center relative text-center mb-7"> </h1>
<h1 className="text-[#181c32] font-semibold dark:text-white mb-3 leading-[27.3px] text-[22.75px]"> {linkSuccess && (
{linkSuccess <span className="text-gray-400 font-medium text-[16.25px] leading-[24.375px]">
? "Sign In to WrenchBoard" Enter a new password to reset
: "Invalid verification link"} </span>
</h1> )}
</div> {linkSuccess && (
{/* If the verification was a success */} <span className="text-gray-400 font-medium text-[16.25px] leading-[24.375px]">
{linkSuccess ? ( We'll send an email to confirm reset
<SuccessfulComponent </span>
password={password}
handlePassword={handlePassword}
// onSubmit={completeSignup}
msgErr={msgError}
loader={linkLoader}
/>
) : (
<ErrorComponent onClick={() => navigate("/login")} />
)} )}
</div> </div>
{/* If the verification was a success */}
{linkSuccess ? (
<SuccessfulComponent
password={password}
confirmPassword={confirmPassword}
handlePassword={handlePassword}
onSubmit={completeReset}
msgErr={msgError}
loader={linkLoader}
onClick={() => navigate("/login")}
/>
) : (
<ErrorComponent onClick={() => navigate("/login")} />
)}
</div> </div>
</div> </div>
)} </div>
</AuthLayout> </AuthLayout>
</> </>
); );
@@ -93,7 +139,9 @@ export default VerifyPassword;
const SuccessfulComponent = ({ const SuccessfulComponent = ({
onSubmit, onSubmit,
onClick,
password, password,
confirmPassword,
handlePassword, handlePassword,
msgErr, msgErr,
loader, loader,
@@ -111,6 +159,17 @@ const SuccessfulComponent = ({
iconName="password" iconName="password"
/> />
</div> </div>
<div className="mb-5">
<InputCom
value={confirmPassword}
inputHandler={handlePassword}
placeholder="● ● ● ● ● ●"
label="Confirm Password"
name="confirm_password"
type="password"
iconName="password"
/>
</div>
{msgErr && ( {msgErr && (
<div className="relative p-4 text-[#912741] bg-[#fcd9e2] border-[#fbc6d3] mb-4 rounded-[0.475rem] text-md font-light leading-[19.5px] text-[13px]"> <div className="relative p-4 text-[#912741] bg-[#fcd9e2] border-[#fbc6d3] mb-4 rounded-[0.475rem] text-md font-light leading-[19.5px] text-[13px]">
{msgErr} {msgErr}
@@ -129,6 +188,15 @@ const SuccessfulComponent = ({
)} )}
</button> </button>
</div> </div>
<div className="signin-area mb-3.5">
<button
onClick={onClick}
type="button"
className={`rounded-[0.475rem] mb-6 text-[15px] font-semibold text-[#009ef7] hover:text-white flex justify-center bg-[#f1faff] hover:bg-[#009ef7] transition-all duration-300 items-center py-[0.8875rem] px-[1.81rem] btn-login`}
>
<span>Return Home</span>
</button>
</div>
</div> </div>
); );
@@ -136,9 +204,9 @@ const ErrorComponent = ({ onClick }) => (
<div className="input-area"> <div className="input-area">
<div className="my-5"> <div className="my-5">
<p className="text-[14px] leading-[19px] text-center text-[#181c32]"> <p className="text-[14px] leading-[19px] text-center text-[#181c32]">
This error occurs because you have already verified this link or the This error occurs because you have already used this link or the link
link has expired. Try login or reset password. If none worked, try to has broken/expired. Start with the reset process again. If it doesn't
create the account from the start. work, try to create the account from the start.
</p> </p>
</div> </div>
+2 -2
View File
@@ -1,5 +1,5 @@
import React from "react"; import React from "react";
import Lottie from "react-lottie"; // import Lottie from "react-lottie";
import { useNavigate } from "react-router-dom"; import { useNavigate } from "react-router-dom";
import * as animationData from "../../assets/images/Lotties/77618-website-404-error-animation.json"; import * as animationData from "../../assets/images/Lotties/77618-website-404-error-animation.json";
@@ -16,7 +16,7 @@ export default function FourZeroFour() {
return ( return (
<div className="flex justify-center items-center w-full h-screen bg-[#232247]"> <div className="flex justify-center items-center w-full h-screen bg-[#232247]">
<div> <div>
<Lottie options={defaultOptions} width={600} height={600} /> {/* <Lottie options={defaultOptions} width={600} height={600} /> */}
<div className="flex justify-center"> <div className="flex justify-center">
<button <button
onClick={() => navigate(-1)} onClick={() => navigate(-1)}