198 lines
5.5 KiB
TypeScript
198 lines
5.5 KiB
TypeScript
import {
|
|
Box,
|
|
Center,
|
|
HStack,
|
|
IconButton,
|
|
Image,
|
|
Input,
|
|
Stack,
|
|
Text,
|
|
VStack,
|
|
} from "@chakra-ui/react";
|
|
import axios from "axios";
|
|
import { useState } from "react";
|
|
import { useNavigate } from "react-router-dom";
|
|
import logo from "../assets/logo.svg";
|
|
import { Button } from "../components/ui/button";
|
|
import { toaster, Toaster } from "../components/ui/toaster";
|
|
import { InputGroup } from "../components/ui/input-group";
|
|
import { LuEye, LuEyeOff } from "react-icons/lu";
|
|
|
|
const SetNewPassword = () => {
|
|
const [password, setPassword] = useState("");
|
|
const [confirmPassword, setConfirmPassword] = useState("");
|
|
const [isLoading, setIsLoading] = useState(false);
|
|
const navigate = useNavigate();
|
|
const queryParams = new URLSearchParams(window.location.search);
|
|
const id = queryParams.get("id");
|
|
const [showOldPassword, setShowOldPassword] = useState(false);
|
|
const [showNewPassword, setShowNewPassword] = useState(false);
|
|
|
|
const handlePasswordSubmit = async () => {
|
|
// Validation
|
|
if (password.length < 8) {
|
|
toaster.create({
|
|
title: "Password must be at least 8 characters long",
|
|
type: "error",
|
|
});
|
|
return;
|
|
}
|
|
|
|
if (password !== confirmPassword) {
|
|
toaster.create({
|
|
title: "Passwords do not match",
|
|
type: "error",
|
|
});
|
|
return;
|
|
}
|
|
|
|
setIsLoading(true);
|
|
|
|
try {
|
|
const res = await axios.post(
|
|
`${import.meta.env.VITE_API_URL}/update-password`,
|
|
{
|
|
password: password,
|
|
confirm_password: confirmPassword,
|
|
id: Number(id),
|
|
}
|
|
);
|
|
|
|
if (res.data.status === "success") {
|
|
toaster.create({
|
|
title: "Password updated successfully",
|
|
type: "success",
|
|
});
|
|
navigate("/login"); // Redirect to login page
|
|
} else {
|
|
toaster.create({
|
|
title: res.data.message || "Failed to update password",
|
|
type: "error",
|
|
});
|
|
}
|
|
} catch (error: any) {
|
|
toaster.create({
|
|
title: error.response?.data?.message || "Something went wrong",
|
|
type: "error",
|
|
});
|
|
} finally {
|
|
setIsLoading(false);
|
|
}
|
|
};
|
|
|
|
return (
|
|
<VStack w="100%" h="100vh" bg="#ffffff">
|
|
<HStack
|
|
boxShadow="rgba(99, 99, 99, 0.2) 0px 2px 8px 0px"
|
|
w="100%"
|
|
ps={8}
|
|
h="7%"
|
|
justifyContent="flex-start"
|
|
>
|
|
<Image w={50} src={logo} />
|
|
</HStack>
|
|
|
|
<Center w="100%" h="93%" p={8}>
|
|
<Box p={8} borderWidth={1} borderRadius="lg" boxShadow="lg" w={"400px"}>
|
|
<Text
|
|
fontSize="20px"
|
|
fontWeight="bold"
|
|
color="#313039"
|
|
marginBottom={"20px"}
|
|
>
|
|
Create a Password
|
|
</Text>
|
|
|
|
<Stack>
|
|
<Box mb={3}>
|
|
<Text color="black" fontSize="12px" mb={2}>
|
|
New password
|
|
</Text>
|
|
<InputGroup
|
|
width={"100%"}
|
|
endElement={
|
|
<IconButton
|
|
aria-label={
|
|
showOldPassword ? "Hide password" : "Show password"
|
|
}
|
|
size="sm"
|
|
onClick={() => setShowOldPassword(!showOldPassword)}
|
|
// _hover={{ bg: "transparent" }}
|
|
bg={"transparent"}
|
|
color={"#000"}
|
|
height={"fit-content"}
|
|
mr={2}
|
|
>
|
|
{showOldPassword ? <LuEye /> : <LuEyeOff />}
|
|
</IconButton>
|
|
}
|
|
>
|
|
<Input
|
|
color="black"
|
|
pl={1}
|
|
fontSize="12px"
|
|
type={showOldPassword ? "password" : "text"}
|
|
border="1px solid grey"
|
|
value={password}
|
|
onChange={(e) => setPassword(e.target.value)}
|
|
size={"sm"}
|
|
/>
|
|
</InputGroup>
|
|
</Box>
|
|
|
|
<Box>
|
|
<Text color="black" mb={2} fontSize="12px">
|
|
Confirm password
|
|
</Text>
|
|
<InputGroup
|
|
width={"100%"}
|
|
endElement={
|
|
<IconButton
|
|
aria-label={
|
|
showNewPassword ? "Hide password" : "Show password"
|
|
}
|
|
size="sm"
|
|
// variant="outline"
|
|
onClick={() => setShowNewPassword(!showNewPassword)}
|
|
bg={"transparent"}
|
|
color={"#000"}
|
|
mr={2}
|
|
>
|
|
{showNewPassword ? <LuEye /> : <LuEyeOff />}
|
|
</IconButton>
|
|
}
|
|
>
|
|
<Input
|
|
color="black"
|
|
pl={1}
|
|
fontSize="12px"
|
|
type={showNewPassword ? "password" : "text"}
|
|
border="1px solid grey"
|
|
value={confirmPassword}
|
|
onChange={(e) => setConfirmPassword(e.target.value)}
|
|
size={"sm"}
|
|
/>
|
|
</InputGroup>
|
|
</Box>
|
|
</Stack>
|
|
|
|
<Button
|
|
loading={isLoading}
|
|
mt={6}
|
|
w="100%"
|
|
bg="#02A0A0"
|
|
color="white"
|
|
onClick={handlePasswordSubmit}
|
|
>
|
|
Confirm Password
|
|
</Button>
|
|
</Box>
|
|
</Center>
|
|
|
|
<Toaster />
|
|
</VStack>
|
|
);
|
|
};
|
|
|
|
export default SetNewPassword;
|