diff --git a/apps/web/src/components/cards/login-card.tsx b/apps/web/src/components/cards/login-card.tsx new file mode 100644 index 0000000..f0a260c --- /dev/null +++ b/apps/web/src/components/cards/login-card.tsx @@ -0,0 +1,108 @@ +import { useState } from "react"; +import apiClient from "../../libs/api.client"; +import { toast } from "react-toastify"; +import { Link } from "react-router-dom"; + +export const LoginCard = () => { + const [email, setEmail] = useState(""); + const [password, setPassword] = useState(""); + + let token = localStorage.getItem("token"); + + const handleSubmit = (event) => { + event.preventDefault(); + + apiClient + .post( + "/user/login", + { + email, + password, + }, + { + headers: { + "Content-Type": "application/json", + }, + } + ) + .then((response) => { + if (response.data.message === "Login successful") { + token = response.data.token; + localStorage.setItem("token", token); + toast.success("Login Successful!", { + position: "bottom-right", + autoClose: 3000, + hideProgressBar: true, + closeOnClick: true, + draggable: true, + }); + setTimeout(() => { + window.location.href = "/app"; + }, 3000); + } else { + toast.error("Login Failed!", { + position: "bottom-right", + autoClose: 3000, + hideProgressBar: true, + closeOnClick: true, + draggable: true, + }); + } + }) + .catch(() => { + toast.error("Login Failed!", { + position: "bottom-right", + autoClose: 3000, + hideProgressBar: true, + closeOnClick: true, + draggable: true, + }); + }); + }; + return ( +
+
+

Sign In

+
+
+
+ +
+
+ setEmail(event.target.value)} + placeholder='Enter your email' + /> +
+
+
+
+ +
+
+ setPassword(event.target.value)} + placeholder='Enter your password' + /> +
+
+ +
+
+

+ Don't have a account, register from{" "} + here. +

+
+ ); +}; diff --git a/apps/web/src/components/cards/register-card.tsx b/apps/web/src/components/cards/register-card.tsx new file mode 100644 index 0000000..a59268b --- /dev/null +++ b/apps/web/src/components/cards/register-card.tsx @@ -0,0 +1,140 @@ +import { useState } from "react"; +import { ToastContainer, toast } from "react-toastify"; +import { Link } from "react-router-dom"; + +import "react-toastify/dist/ReactToastify.css"; +import apiClient from "../../libs/api.client"; + +export const RegisterCard = () => { + const [email, setEmail] = useState(""); + const [password, setPassword] = useState(""); + const [firstName, setFirstName] = useState(""); + const [lastName, setLastName] = useState(""); + + const handleSubmit = (event) => { + event.preventDefault(); + + apiClient + .post( + "/user/register", + { + email, + password, + firstName, + lastName, + }, + { + headers: { + "Content-Type": "application/json", + }, + } + ) + .then((response) => { + if (response.data.email === email) { + toast.success("Register Successful!", { + position: "bottom-right", + autoClose: 3000, + hideProgressBar: true, + closeOnClick: true, + draggable: true, + }); + setTimeout(() => { + window.location.href = "/verify"; + }, 3000); + } else { + toast.error("Register Failed!", { + position: "bottom-right", + autoClose: 3000, + hideProgressBar: true, + closeOnClick: true, + draggable: true, + }); + } + }) + .catch(() => { + toast.error("Register Failed!", { + position: "bottom-right", + autoClose: 3000, + hideProgressBar: true, + closeOnClick: true, + draggable: true, + }); + }); + }; + + return ( +
+
+

Sign In

+
+
+
+ +
+
+ setEmail(event.target.value)} + placeholder='Enter your email' + /> +
+
+
+
+ +
+
+ setPassword(event.target.value)} + placeholder='Enter your password' + /> +
+
+
+
+ +
+
+ setFirstName(event.target.value)} + placeholder='Enter your firstName' + /> +
+
+
+
+ +
+
+ setLastName(event.target.value)} + placeholder='Enter your lastName' + /> +
+
+ +
+
+

+ Already have a account? Login from here. +

+
+ ); +}; diff --git a/apps/web/src/pages/about.jsx b/apps/web/src/pages/about.jsx index 4354596..aa84d6f 100644 --- a/apps/web/src/pages/about.jsx +++ b/apps/web/src/pages/about.jsx @@ -4,7 +4,7 @@ import Navbar from "../components/navbar"; function Home() { return ( <> - +

Guides

diff --git a/apps/web/src/pages/app.jsx b/apps/web/src/pages/app.jsx index d96b783..ed66f12 100644 --- a/apps/web/src/pages/app.jsx +++ b/apps/web/src/pages/app.jsx @@ -16,7 +16,7 @@ function Player() { ]); useEffect(() => { - if (!token) return (window.location.href = "/login"); + if (!token) return (window.location.href = "/"); apiClient .get("/challenge/progress", { @@ -25,9 +25,9 @@ function Player() { }, }) .then((res) => { - if (!Array.isArray(res.data)) return (window.location.href = "/login"); + if (!Array.isArray(res.data)) return (window.location.href = "/"); if (res.data.message === "Invalid token") - return (window.location.href = "/login"); + return (window.location.href = "/"); setMachines(res.data); }); }, [token]); diff --git a/apps/web/src/pages/home.jsx b/apps/web/src/pages/home.jsx index 3cda7da..55d0d6b 100644 --- a/apps/web/src/pages/home.jsx +++ b/apps/web/src/pages/home.jsx @@ -1,13 +1,56 @@ -import "../styles/App.css"; +import "../styles/home.styles.css"; import "react-toastify/dist/ReactToastify.css"; -// import { Link } from "react-router-dom"; +import apiClient from "../libs/api.client"; import Navbar from "../components/navbar"; +import { useEffect, useState } from "react"; +import { LoginCard } from "../components/cards/login-card"; +import { RegisterCard } from "../components/cards/register-card"; function Home() { + const [user, setUser] = useState(null); + useEffect(() => { + const token = localStorage.getItem("token"); + + if (!token) return; + + apiClient + .get("/user/whoami", { + headers: { + Authorization: "Bearer " + token, + }, + }) + .then((res) => { + if (res.data.error) return; + + if (res.data.message === "Invalid token") return; + setUser(res.data); + }); + }, []); + return (
- -

hello

+ +
+ {user === null ? ( +
+ + +
+ ) : ( +
+
+ {/*

+ You are currently in {user.team_name} team. Your team has{" "} + {user.team_score} points. +

*/} +
+
+ )} +
); } diff --git a/apps/web/src/pages/leaderboard.jsx b/apps/web/src/pages/leaderboard.jsx index 6a4b29d..1e9dd03 100644 --- a/apps/web/src/pages/leaderboard.jsx +++ b/apps/web/src/pages/leaderboard.jsx @@ -9,7 +9,7 @@ function Leaderboard() { useEffect(() => { const token = localStorage.getItem("token"); - if (!token) return (window.location.href = "/login"); + if (!token) return (window.location.href = "/"); apiClient .get("/stats/leaderboard", { @@ -18,8 +18,7 @@ function Leaderboard() { }, }) .then((response) => { - if (!Array.isArray(response.data)) - return (window.location.href = "/login"); + if (!Array.isArray(response.data)) return (window.location.href = "/"); setLeaderboard(response.data); }) .catch(() => { diff --git a/apps/web/src/pages/news.jsx b/apps/web/src/pages/news.jsx index c17837f..4f781e7 100644 --- a/apps/web/src/pages/news.jsx +++ b/apps/web/src/pages/news.jsx @@ -4,7 +4,7 @@ import Navbar from "../components/navbar"; function News() { return ( <> - + {/*

News

diff --git a/apps/web/src/pages/verify.jsx b/apps/web/src/pages/verify.jsx index 3b02903..ad2d342 100644 --- a/apps/web/src/pages/verify.jsx +++ b/apps/web/src/pages/verify.jsx @@ -32,7 +32,7 @@ function Home() { draggable: true, }); setTimeout(() => { - window.location.href = "/login"; + window.location.href = "/"; }, 3000); } else { toast.error("Email Verification Failed!", { diff --git a/apps/web/src/pages/whoami.jsx b/apps/web/src/pages/whoami.jsx index 983c92b..0b54d77 100644 --- a/apps/web/src/pages/whoami.jsx +++ b/apps/web/src/pages/whoami.jsx @@ -14,7 +14,7 @@ function WhoAmI() { useEffect(() => { const token = localStorage.getItem("token"); - if (!token) return (window.location.href = "/login"); + if (!token) return (window.location.href = "/"); apiClient .get("/user/whoami", { @@ -23,10 +23,10 @@ function WhoAmI() { }, }) .then((res) => { - if (res.data.error) return (window.location.href = "/login"); + if (res.data.error) return (window.location.href = "/"); if (res.data.message === "Invalid token") - return (window.location.href = "/login"); + return (window.location.href = "/"); setUserWhoami(res.data); }); @@ -37,10 +37,10 @@ function WhoAmI() { }, }) .then((res) => { - if (res.data.error) return (window.location.href = "/login"); + if (res.data.error) return (window.location.href = "/"); if (res.data.message === "Invalid token") - return (window.location.href = "/login"); + return (window.location.href = "/"); setTeamWhoami(res.data); }); @@ -51,9 +51,9 @@ function WhoAmI() { }, }) .then((res) => { - if (res.data.error) return (window.location.href = "/login"); + if (res.data.error) return (window.location.href = "/"); if (res.data.message === "Invalid token") - return (window.location.href = "/login"); + return (window.location.href = "/"); setTeamStats(res.data); }); }, []); diff --git a/apps/web/src/styles/App.css b/apps/web/src/styles/App.css index e62c4d9..a2828bb 100644 --- a/apps/web/src/styles/App.css +++ b/apps/web/src/styles/App.css @@ -20,6 +20,13 @@ } } +.action-card { + width: 100%; + display: flex; + flex-direction: row; + align-items: center; +} + .card { padding: 2em; } diff --git a/apps/web/src/styles/home.styles.css b/apps/web/src/styles/home.styles.css new file mode 100644 index 0000000..f857508 --- /dev/null +++ b/apps/web/src/styles/home.styles.css @@ -0,0 +1,9 @@ +.auht-grid { + display: flex; + flex-direction: row; + gap: 3rem; + align-items: center; + justify-content: center; + width: 100%; + margin: auto; +} diff --git a/apps/web/src/styles/navbar.styles.css b/apps/web/src/styles/navbar.styles.css index 8ab072e..8d2ea9b 100644 --- a/apps/web/src/styles/navbar.styles.css +++ b/apps/web/src/styles/navbar.styles.css @@ -11,13 +11,6 @@ font-weight: bold; } -.action-card { - width: 100%; - display: flex; - flex-direction: row; - align-items: center; -} - .action-card .right { width: 100%; height: 100%;