From c3270a9543b4b23f82d6f7b00084d72f444d5848 Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 22:55:24 +0100 Subject: [PATCH 01/11] remove login page from layout --- src/pages/Login/LoginPage.jsx | 9 ++++++--- src/router.js | 8 ++++---- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/src/pages/Login/LoginPage.jsx b/src/pages/Login/LoginPage.jsx index 95a194a..eca8559 100644 --- a/src/pages/Login/LoginPage.jsx +++ b/src/pages/Login/LoginPage.jsx @@ -1,12 +1,15 @@ import styles from "./LoginPage.module.css"; import LoginForm from "../../components/form/form.jsx"; +import Background from "../../components/background/background.jsx"; function LoginPage() { - return ( + return +
- +
- ); + +
} export default LoginPage; diff --git a/src/router.js b/src/router.js index c3351c5..806f2ea 100644 --- a/src/router.js +++ b/src/router.js @@ -4,6 +4,10 @@ import HomePage from "./pages/Home/HomePage"; import LoginPage from "./pages/Login/LoginPage"; const router = createBrowserRouter([ + { + path: "/login", + Component: LoginPage, + }, { path: "/", Component: Layout, @@ -11,10 +15,6 @@ const router = createBrowserRouter([ { path: "/", Component: HomePage, - }, - { - path: "/login", - Component: LoginPage, } ] } From d03b373eb7fe3436d8954e478baf09ca8409a17b Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 22:55:33 +0100 Subject: [PATCH 02/11] Update login function --- src/utils/login.js | 52 ++++++++++++++++++++++------------------------ 1 file changed, 25 insertions(+), 27 deletions(-) diff --git a/src/utils/login.js b/src/utils/login.js index 4174113..a08151b 100644 --- a/src/utils/login.js +++ b/src/utils/login.js @@ -3,31 +3,29 @@ import getXSRFToken from "./getXSRF.js"; export default async function login(email, password) { const csrfToken = await getXSRFToken(); - - await fetch('http://localhost:8000/api/login', { - method: 'POST', - credentials: 'include', - headers: { - 'Content-Type': 'application/json', - 'X-XSRF-TOKEN': csrfToken, - 'Accept': 'application/json' - }, - body: JSON.stringify({ - email: email, - password: password - }) - }) - .then(response => { - console.log('Code HTTP :', response.status); - if (!response.ok) { - throw new Error(`Erreur HTTP ${response.status}`); - } - return response.json(); - }) - .then(data => { - console.log('Connexion réussie ! Données utilisateur :', data); - }) - .catch(error => { - console.error('Erreur lors de la connexion :', error.message); + try { + const response = await fetch('http://localhost:8000/api/users/login', { + method: 'POST', + credentials: 'include', + headers: { + 'Content-Type': 'application/json', + 'X-XSRF-TOKEN': csrfToken, + 'Accept': 'application/json' + }, + body: JSON.stringify({ email, password }) }); -} \ No newline at end of file + + console.log('Code HTTP :', response.status); + + if (!response.ok) { + throw new Error(`Erreur HTTP ${response.status}`); + } + + const data = await response.json(); + console.log('Connexion réussie ! Données utilisateur :', data); + + return { status: response.status, data }; + } catch (error) { + return error; + } +} From 229cc27be26fce5cb2302f4cdc14fa4f874c7e18 Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 22:55:42 +0100 Subject: [PATCH 03/11] use ui components --- src/components/form/form.jsx | 60 +++++++++++------------------------- 1 file changed, 18 insertions(+), 42 deletions(-) diff --git a/src/components/form/form.jsx b/src/components/form/form.jsx index fc46bcd..18e31f7 100644 --- a/src/components/form/form.jsx +++ b/src/components/form/form.jsx @@ -1,47 +1,27 @@ -/*import { useState } from "react"; -import login from "../../utils/login.js"; -import getUser from "../../utils/getUser.js"; -import styles from "./form.module.css"; -function LoginForm({ className }) { - const [email, setEmail] = useState(''); - const [password, setPassword] = useState(''); - async function handleSubmit(e) { - e.preventDefault(); - await login(email, password); - getUser(); - } - return ( -
-
- setEmail(e.target.value)} required/> -
- -
- setPassword(e.target.value)} required/> -
-
-
- -
-
- ); -} -export default LoginForm;*/ - import { useState } from "react"; import login from "../../utils/login.js"; import getUser from "../../utils/getUser.js"; import styles from "./form.module.css"; +import Button from "../ui/button/button.jsx"; +import Input from "../ui/input/input.jsx"; +import { useNavigate } from "react-router"; function LoginForm({ className }) { const [email, setEmail] = useState(''); const [password, setPassword] = useState(''); const [showPassword, setShowPassword] = useState(false); + let navigate = useNavigate(); + async function handleSubmit(e) { e.preventDefault(); - await login(email, password); - getUser(); + + const res = await login(email, password); + + if(res.status === 200) { + await getUser(); + navigate("/"); + } } const toggleShowPassword = () => { @@ -51,27 +31,22 @@ function LoginForm({ className }) { return (
- setEmail(e.target.value)} - required + style={{ width: '100%' }} />
- setPassword(e.target.value)} - required - style={{ width: '100%', paddingRight: '40px' }} + style={{ width: '100%' }} />
+
- +
); From 9937e0e2b9e0b55410b45e3c2ca1ddc48e831ab2 Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:27:36 +0100 Subject: [PATCH 04/11] Create auth context --- src/contexts/auth/AuthContext.js | 3 +++ src/contexts/auth/authProvider.jsx | 35 ++++++++++++++++++++++++++++++ 2 files changed, 38 insertions(+) create mode 100644 src/contexts/auth/AuthContext.js create mode 100644 src/contexts/auth/authProvider.jsx diff --git a/src/contexts/auth/AuthContext.js b/src/contexts/auth/AuthContext.js new file mode 100644 index 0000000..885fd0e --- /dev/null +++ b/src/contexts/auth/AuthContext.js @@ -0,0 +1,3 @@ +import { createContext } from "react"; + +export const AuthContext = createContext(null); diff --git a/src/contexts/auth/authProvider.jsx b/src/contexts/auth/authProvider.jsx new file mode 100644 index 0000000..a46d3c3 --- /dev/null +++ b/src/contexts/auth/authProvider.jsx @@ -0,0 +1,35 @@ +import { useState, useEffect } from "react"; +import loginFunction from "../../utils/login.js"; +import getUser from "../../utils/getUser.js"; +import { AuthContext } from "./AuthContext"; + + +export function AuthProvider({ children }) { + const [user, setUser] = useState(null); + const [loading, setLoading] = useState(true); + + useEffect(() => { + (async () => { + const u = await getUser(); + setUser(u); + setLoading(false); + })(); + }, []); + + const login = async (email, password) => { + await loginFunction(email, password); + const u = await getUser(); + setUser(u); + }; + + const logout = async () => { + // TODO: Appeller fonction logout + setUser(null); + }; + + return ( + + {children} + + ); +} From 7e3c60825a18e3ab0c05a6f9fae663f74445b9ee Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:27:53 +0100 Subject: [PATCH 05/11] Set auth context --- src/main.jsx | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/main.jsx b/src/main.jsx index 088afa5..6b79e8c 100644 --- a/src/main.jsx +++ b/src/main.jsx @@ -3,10 +3,13 @@ import { createRoot } from 'react-dom/client' import './index.css' import { RouterProvider } from "react-router"; import router from './router'; +import { AuthProvider } from "./contexts/auth/authProvider.jsx"; createRoot(document.getElementById('root')).render( - + + + , ) From 6e01fca87dfe6fbb7c65c9f5b30e1b5bcb2d0d5b Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:28:01 +0100 Subject: [PATCH 06/11] Update getUSer function --- src/utils/getUser.js | 29 +++++++++++++++++++---------- 1 file changed, 19 insertions(+), 10 deletions(-) diff --git a/src/utils/getUser.js b/src/utils/getUser.js index 5345926..6826525 100644 --- a/src/utils/getUser.js +++ b/src/utils/getUser.js @@ -1,12 +1,21 @@ export default async function getUser() { - await fetch('http://localhost:8000/api/me', { - method: 'GET', - credentials: 'include', - headers: { - 'Accept': 'application/json' + try { + const res = await fetch('http://localhost:8000/api/me', { + method: 'GET', + credentials: 'include', + headers: { + 'Accept': 'application/json' + } + }); + + if (!res.ok) { + throw new Error(`Erreur serveur : ${res.status}`); } - }) - .then(res => res.json()) - .then(data => console.log('Utilisateur connecté :', data)) - .catch(err => console.error('Erreur :', err)); -} \ No newline at end of file + + const data = await res.json(); + return data; + } catch (err) { + console.error('Erreur :', err); + return null; + } +} From b79c46007715770f72196603a1a1d4a299d13260 Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:28:09 +0100 Subject: [PATCH 07/11] Protect routes --- src/layout.jsx | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/src/layout.jsx b/src/layout.jsx index b159981..4689a4e 100644 --- a/src/layout.jsx +++ b/src/layout.jsx @@ -2,10 +2,18 @@ import { Outlet } from "react-router"; import Footer from "./components/Footer/Footer.jsx" import Header from "./components/Header/Header.jsx"; import Background from "./components/background/background.jsx"; +import { Navigate } from "react-router"; +import { useContext} from "react"; +import { AuthContext } from "./contexts/auth/AuthContext.js"; function Layout(){ + const { user, loading } = useContext(AuthContext); + + if (loading) return

Loading

; + if (!user) return ; + return (
From 6e97788f00a8136a3b105c57305b1773db0079bb Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:31:07 +0100 Subject: [PATCH 08/11] Rename login Form --- src/components/{form => loginform}/form.jsx | 2 +- .../{form/form.module.css => loginform/loginForm.module.css} | 0 src/pages/Login/LoginPage.jsx | 2 +- 3 files changed, 2 insertions(+), 2 deletions(-) rename src/components/{form => loginform}/form.jsx (98%) rename src/components/{form/form.module.css => loginform/loginForm.module.css} (100%) diff --git a/src/components/form/form.jsx b/src/components/loginform/form.jsx similarity index 98% rename from src/components/form/form.jsx rename to src/components/loginform/form.jsx index 18e31f7..fa72f43 100644 --- a/src/components/form/form.jsx +++ b/src/components/loginform/form.jsx @@ -1,7 +1,7 @@ import { useState } from "react"; import login from "../../utils/login.js"; import getUser from "../../utils/getUser.js"; -import styles from "./form.module.css"; +import styles from "./loginForm.module.css"; import Button from "../ui/button/button.jsx"; import Input from "../ui/input/input.jsx"; import { useNavigate } from "react-router"; diff --git a/src/components/form/form.module.css b/src/components/loginform/loginForm.module.css similarity index 100% rename from src/components/form/form.module.css rename to src/components/loginform/loginForm.module.css diff --git a/src/pages/Login/LoginPage.jsx b/src/pages/Login/LoginPage.jsx index eca8559..2a08696 100644 --- a/src/pages/Login/LoginPage.jsx +++ b/src/pages/Login/LoginPage.jsx @@ -1,5 +1,5 @@ import styles from "./LoginPage.module.css"; -import LoginForm from "../../components/form/form.jsx"; +import LoginForm from "../../components/loginform/form.jsx"; import Background from "../../components/background/background.jsx"; function LoginPage() { From 840695cf902f65679d5fa1047577decfe9c8699d Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:34:46 +0100 Subject: [PATCH 09/11] Rename login Form --- src/components/loginform/{form.jsx => loginForm.jsx} | 2 +- src/pages/Login/LoginPage.jsx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) rename src/components/loginform/{form.jsx => loginForm.jsx} (100%) diff --git a/src/components/loginform/form.jsx b/src/components/loginform/loginForm.jsx similarity index 100% rename from src/components/loginform/form.jsx rename to src/components/loginform/loginForm.jsx index fa72f43..753e525 100644 --- a/src/components/loginform/form.jsx +++ b/src/components/loginform/loginForm.jsx @@ -6,11 +6,11 @@ import Button from "../ui/button/button.jsx"; import Input from "../ui/input/input.jsx"; import { useNavigate } from "react-router"; + function LoginForm({ className }) { const [email, setEmail] = useState(''); const [password, setPassword] = useState(''); const [showPassword, setShowPassword] = useState(false); - let navigate = useNavigate(); async function handleSubmit(e) { diff --git a/src/pages/Login/LoginPage.jsx b/src/pages/Login/LoginPage.jsx index 2a08696..fcea9bb 100644 --- a/src/pages/Login/LoginPage.jsx +++ b/src/pages/Login/LoginPage.jsx @@ -1,5 +1,5 @@ import styles from "./LoginPage.module.css"; -import LoginForm from "../../components/loginform/form.jsx"; +import LoginForm from "../../components/loginform/loginForm.jsx"; import Background from "../../components/background/background.jsx"; function LoginPage() { From 7705666c3bc09ba716c6df91eccb9272e92ae078 Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sat, 15 Nov 2025 23:43:06 +0100 Subject: [PATCH 10/11] Fix redirect on login --- src/components/loginform/loginForm.jsx | 15 +++++---------- src/contexts/auth/authProvider.jsx | 4 +++- 2 files changed, 8 insertions(+), 11 deletions(-) diff --git a/src/components/loginform/loginForm.jsx b/src/components/loginform/loginForm.jsx index 753e525..edc6c55 100644 --- a/src/components/loginform/loginForm.jsx +++ b/src/components/loginform/loginForm.jsx @@ -1,10 +1,9 @@ -import { useState } from "react"; -import login from "../../utils/login.js"; -import getUser from "../../utils/getUser.js"; +import { useState, useContext } from "react"; import styles from "./loginForm.module.css"; import Button from "../ui/button/button.jsx"; import Input from "../ui/input/input.jsx"; import { useNavigate } from "react-router"; +import { AuthContext } from "../../contexts/auth/AuthContext.js"; function LoginForm({ className }) { @@ -12,16 +11,12 @@ function LoginForm({ className }) { const [password, setPassword] = useState(''); const [showPassword, setShowPassword] = useState(false); let navigate = useNavigate(); + const { login } = useContext(AuthContext); async function handleSubmit(e) { e.preventDefault(); - - const res = await login(email, password); - - if(res.status === 200) { - await getUser(); - navigate("/"); - } + await login(email, password); + navigate("/"); } const toggleShowPassword = () => { diff --git a/src/contexts/auth/authProvider.jsx b/src/contexts/auth/authProvider.jsx index a46d3c3..7151a96 100644 --- a/src/contexts/auth/authProvider.jsx +++ b/src/contexts/auth/authProvider.jsx @@ -17,9 +17,11 @@ export function AuthProvider({ children }) { }, []); const login = async (email, password) => { - await loginFunction(email, password); + const res = await loginFunction(email, password); + if (!res || res.status !== 200) throw new Error("Login error"); const u = await getUser(); setUser(u); + return res; }; const logout = async () => { From d004c2073ea029a203c1e55e331839746557a778 Mon Sep 17 00:00:00 2001 From: T'JAMPENS QUENTIN p2406187 Date: Sun, 16 Nov 2025 02:14:28 +0100 Subject: [PATCH 11/11] Create register page --- src/pages/Register/RegisterPage.jsx | 105 +++++++++++++++++++++ src/pages/Register/RegisterPage.module.css | 29 ++++++ src/router.js | 5 + src/utils/register.js | 30 ++++++ 4 files changed, 169 insertions(+) create mode 100644 src/pages/Register/RegisterPage.jsx create mode 100644 src/pages/Register/RegisterPage.module.css create mode 100644 src/utils/register.js diff --git a/src/pages/Register/RegisterPage.jsx b/src/pages/Register/RegisterPage.jsx new file mode 100644 index 0000000..489858d --- /dev/null +++ b/src/pages/Register/RegisterPage.jsx @@ -0,0 +1,105 @@ +import styles from "./RegisterPage.module.css"; +import Background from "../../components/background/background.jsx"; +import Input from "../../components/ui/input/input.jsx"; +import Button from "../../components/ui/button/button.jsx"; +import { useState } from "react"; +import register from "../../utils/register.js"; +import { useNavigate } from "react-router"; + + +function RegisterPage() { + + const navigate = useNavigate(); + + const [email, setEmail] = useState(""); + const [password, setPassword] = useState(""); + const [name, setName] = useState(""); + const [lastName, setLastName] = useState(""); + + const [showPassword, setShowPassword] = useState(false); + + + async function handleSubmit(e) { + e.preventDefault(); + const res = await register(email, password, name, lastName); + if (!res || res.status !== 200) throw new Error("Register error"); + navigate("/login"); + } + + return + +
+ +
+ +

Créer un compte

+ +
+ setName(e.target.value)} + style={{ width: '100%' }} + /> +
+ +
+ setLastName(e.target.value)} + style={{ width: '100%' }} + /> +
+ +
+ setEmail(e.target.value)} + style={{ width: '100%' }} + /> +
+
+
+ setPassword(e.target.value)} + style={{ width: '100%' }} + /> + +
+
+ +
+ + +
+
+
+ +
+} + +export default RegisterPage; + + diff --git a/src/pages/Register/RegisterPage.module.css b/src/pages/Register/RegisterPage.module.css new file mode 100644 index 0000000..7a379ee --- /dev/null +++ b/src/pages/Register/RegisterPage.module.css @@ -0,0 +1,29 @@ +.container { + position: relative; + z-index: 2; + display: flex; + width: 30%; + justify-content: center; + align-items: center; + padding: 20px; + border-radius:12px; +} + +:global(.glassCard) { + --glass-bg: #ffffff9f; +} +.logButton{ + display: flex; + justify-content: center; + flex-direction: column; + align-items: center; + margin-top: 12px; +} +.formGroup{ + margin-top:23px; +} + +h1 { + overflow: visible; + text-align: center; +} \ No newline at end of file diff --git a/src/router.js b/src/router.js index 806f2ea..791e290 100644 --- a/src/router.js +++ b/src/router.js @@ -2,12 +2,17 @@ import { createBrowserRouter } from "react-router"; import Layout from "./layout.jsx"; import HomePage from "./pages/Home/HomePage"; import LoginPage from "./pages/Login/LoginPage"; +import RegisterPage from "./pages/Register/RegisterPage.jsx"; const router = createBrowserRouter([ { path: "/login", Component: LoginPage, }, + { + path: "/register", + Component: RegisterPage, + }, { path: "/", Component: Layout, diff --git a/src/utils/register.js b/src/utils/register.js new file mode 100644 index 0000000..1612bf8 --- /dev/null +++ b/src/utils/register.js @@ -0,0 +1,30 @@ +import getXSRFToken from "./getXSRF.js"; + +export default async function register(email, password, name, lastname) { + const csrfToken = await getXSRFToken(); + + try { + const response = await fetch('http://localhost:8000/api/users/register', { + method: 'POST', + credentials: 'include', + headers: { + 'Content-Type': 'application/json', + 'X-XSRF-TOKEN': csrfToken, + 'Accept': 'application/json' + }, + body: JSON.stringify({ email, password, name, lastname }), + }); + + console.log('Code HTTP :', response.status); + + if (!response.ok) { + throw new Error(`Erreur HTTP ${response.status}`); + } + + const data = await response.json(); + + return { status: response.status, data }; + } catch (error) { + return error; + } +}