From 16c8e4377b87936b3910ed3c0f1fd811ad8d482f Mon Sep 17 00:00:00 2001 From: afazio1 Date: Thu, 11 Apr 2024 16:48:58 -0400 Subject: [PATCH] finish login, logout, session context --- frontend/src/App.tsx | 55 +++++++++++++------ frontend/src/contexts/session.ts | 17 ++++++ frontend/src/hooks/sessionRedirect.ts | 14 +++++ frontend/src/screens/Login.tsx | 78 +++++++++++++++------------ frontend/src/screens/Signup.tsx | 10 ++-- 5 files changed, 121 insertions(+), 53 deletions(-) create mode 100644 frontend/src/contexts/session.ts create mode 100644 frontend/src/hooks/sessionRedirect.ts diff --git a/frontend/src/App.tsx b/frontend/src/App.tsx index c44ef54..73dfb70 100644 --- a/frontend/src/App.tsx +++ b/frontend/src/App.tsx @@ -1,31 +1,56 @@ import "./styles/App.css"; -import { Link } from 'react-router-dom'; +import { Link, useNavigate } from 'react-router-dom'; import MainSearch from './components/MainSearch'; +import { SessionContext, destroySessionCookie, getSessionCookie } from "./contexts/session"; +import { useState, useEffect, useContext } from "react"; export default function App() { + const [session, setSession] = useState(getSessionCookie()); + const navigate = useNavigate(); + + // Redirect to login if session is undefined + useEffect( + () => { + setSession(getSessionCookie()); + if (session === undefined) { + navigate("/login"); + } + }, + [session, navigate] + ); return ( <> - -
- PeerNotes Logo - -
+ + +
+ PeerNotes Logo + +
+
) } - function Navbar() { + const session = useContext(SessionContext); + + const links = session ? ( + <> + Home + Logout + + ): ( + Login + ) return ( ); } \ No newline at end of file diff --git a/frontend/src/contexts/session.ts b/frontend/src/contexts/session.ts new file mode 100644 index 0000000..ce77016 --- /dev/null +++ b/frontend/src/contexts/session.ts @@ -0,0 +1,17 @@ +import React from "react"; + +type SessionContextType = string | undefined; + +export const getSessionCookie = () => { + const sessionCookie = document.cookie + .split('; ') + .find(row => row.startsWith('token=')) + ?.split('=')[1]; + return sessionCookie; +} +export const destroySessionCookie = () => { + document.cookie = "token=; Max-Age=0;" +} + +export const SessionContext = React.createContext(getSessionCookie()); + diff --git a/frontend/src/hooks/sessionRedirect.ts b/frontend/src/hooks/sessionRedirect.ts new file mode 100644 index 0000000..c90d30a --- /dev/null +++ b/frontend/src/hooks/sessionRedirect.ts @@ -0,0 +1,14 @@ +import { useEffect, useContext } from "react"; +import { useNavigate } from "react-router-dom"; +import { SessionContext } from "../contexts/session"; + +export const useSessionRedirect = () => { + const session = useContext(SessionContext); + const navigate = useNavigate(); + // Redirect to home if session is defined + useEffect(() => { + if (session !== undefined) { + navigate('/'); + } + }, [session, navigate]) +} \ No newline at end of file diff --git a/frontend/src/screens/Login.tsx b/frontend/src/screens/Login.tsx index 928ef90..23a1cd5 100644 --- a/frontend/src/screens/Login.tsx +++ b/frontend/src/screens/Login.tsx @@ -1,40 +1,48 @@ -import { Link } from "react-router-dom" +import { Link, useNavigate } from "react-router-dom" import "../styles/Login.css" import { FormEvent } from "react"; +import { useSessionRedirect } from "../hooks/sessionRedirect"; export default function Login() { - function handleSubmit(e: FormEvent) { - e.preventDefault(); - const formData = new FormData(e.target as HTMLFormElement); - const username = formData.get('username'); - const password = formData.get('password'); - fetch('http://localhost:8000/api/login/', { - method: 'POST', - credentials: 'include', - headers: { - 'Content-Type': 'application/json', - }, - body: JSON.stringify({ username, password }), - }) - .catch((error) => { - console.error('Error:', error); - }); - } - return ( -
-
-

Login

-
- - -
-
- - -
- -

or Sign up

-
-
- ); + const navigate = useNavigate(); + + useSessionRedirect(); + + function handleSubmit(e: FormEvent) { + e.preventDefault(); + const formData = new FormData(e.target as HTMLFormElement); + const username = formData.get('username'); + const password = formData.get('password'); + fetch('http://localhost:8000/api/login/', { + method: 'POST', + credentials: 'include', + headers: { + 'Content-Type': 'application/json', + }, + body: JSON.stringify({ username, password }), + }) + .then(() => { + navigate('/'); + }) + .catch((error) => { + console.error('Error:', error); + }); + } + return ( +
+
+

Login

+
+ + +
+
+ + +
+ +

or Sign up

+
+
+ ); } \ No newline at end of file diff --git a/frontend/src/screens/Signup.tsx b/frontend/src/screens/Signup.tsx index c207581..9022619 100644 --- a/frontend/src/screens/Signup.tsx +++ b/frontend/src/screens/Signup.tsx @@ -1,7 +1,11 @@ -import { Link } from "react-router-dom"; +import { Link, useNavigate } from "react-router-dom"; import "../styles/Login.css" import { FormEvent } from "react"; +import { useSessionRedirect } from "../hooks/sessionRedirect"; export default function Signup() { + const navigate = useNavigate(); + useSessionRedirect(); + function handleSubmit(e: FormEvent) { e.preventDefault(); const formData = new FormData(e.target as HTMLFormElement); @@ -16,8 +20,8 @@ export default function Signup() { body: JSON.stringify({ email, username, password }), }) .then(response => response.json()) - .then(data => { - console.log('Success:', data); + .then(() => { + navigate('/login'); }) .catch((error) => { console.error('Error:', error);