[0c6b92a] | 1 | import React, {useContext, useState} from "react";
|
---|
| 2 | import {Link, useLocation, useNavigate} from "react-router-dom";
|
---|
[d565449] | 3 | import styles from "./Login.module.css";
|
---|
| 4 | import illustration from "../../assets/illustration_img.png";
|
---|
[0c6b92a] | 5 | import Logo from "../../components/Logo/Logo.jsx";
|
---|
| 6 | import HttpService from "../../scripts/net/HttpService.js";
|
---|
| 7 | import {useAppContext} from "../../components/AppContext/AppContext.jsx";
|
---|
[79a0317] | 8 | import config, {API_BASE_URL} from "../../scripts/net/netconfig.js";
|
---|
| 9 | import google_icon from "../../assets/Logo-google-icon-PNG.png"
|
---|
| 10 | import github_icon from "../../assets/github-mark-white.png";
|
---|
| 11 | import { v4 as uuidv4 } from 'uuid';
|
---|
[d565449] | 12 |
|
---|
[0c6b92a] | 13 | const LoginPage = () => {
|
---|
| 14 | const [formUsername, setFormUsername] = useState("");
|
---|
| 15 | const [password, setPassword] = useState("");
|
---|
| 16 | const [error, setError] = useState(null);
|
---|
| 17 | const navigate = useNavigate();
|
---|
| 18 | const location = useLocation();
|
---|
[d565449] | 19 |
|
---|
[0c6b92a] | 20 | const {setUsername, setIsAuthenticated} = useAppContext();
|
---|
[d565449] | 21 |
|
---|
[0c6b92a] | 22 | const {targetPath} = location.state || {targetPath: {pathname: "/"}};
|
---|
[d565449] | 23 |
|
---|
[0c6b92a] | 24 | const payload = {
|
---|
| 25 | username: formUsername,
|
---|
| 26 | password: password,
|
---|
| 27 | };
|
---|
[d565449] | 28 |
|
---|
[0c6b92a] | 29 | const handleLogin = async () => {
|
---|
| 30 | const httpService = new HttpService();
|
---|
[79a0317] | 31 | return httpService.post(config.auth.login, payload);
|
---|
[0c6b92a] | 32 | };
|
---|
| 33 |
|
---|
| 34 | const login = async (e) => {
|
---|
| 35 | e.preventDefault();
|
---|
| 36 |
|
---|
| 37 | handleLogin()
|
---|
| 38 | .then(resp => {
|
---|
| 39 | if (resp.token) {
|
---|
[79a0317] | 40 | navigate(targetPath);
|
---|
[0c6b92a] | 41 | localStorage.setItem("token", resp.token);
|
---|
| 42 | setUsername(resp.username);
|
---|
| 43 | setIsAuthenticated(true);
|
---|
[79a0317] | 44 | console.log("ROLES", resp.roles);
|
---|
[0c6b92a] | 45 | } else {
|
---|
| 46 | setError("Invalid username or password.");
|
---|
| 47 | }
|
---|
| 48 | }).catch(reason => {
|
---|
| 49 | console.error("Login failed", reason);
|
---|
[79a0317] | 50 | setError("Login failed. Please try again.");
|
---|
| 51 | });
|
---|
| 52 | };
|
---|
| 53 |
|
---|
| 54 | const continueWithGitHub = async () => {
|
---|
| 55 | const httpService = new HttpService();
|
---|
| 56 | httpService.setResponseType('text');
|
---|
| 57 | const state = await httpService.get(config.auth.oauth.github.state)
|
---|
| 58 | const clientId = 'Iv23liqzhX5wMYNDHtnz';
|
---|
| 59 | const redirectUri = encodeURI(`${API_BASE_URL}/oauth/callback/github`);
|
---|
[0c6b92a] | 60 |
|
---|
[79a0317] | 61 | const githubAuthUrl = `https://github.com/login/oauth/authorize?client_id=${encodeURI(clientId)}&redirect_uri=${redirectUri}&state=${encodeURI(state)}&scope=user:email`;
|
---|
| 62 |
|
---|
| 63 | window.location.href = githubAuthUrl;
|
---|
| 64 |
|
---|
| 65 | };
|
---|
| 66 |
|
---|
| 67 | const continueWithGoogle = async () => {
|
---|
| 68 | console.log("Continue with Google");
|
---|
| 69 | const httpService = new HttpService();
|
---|
| 70 | httpService.setResponseType('text');
|
---|
| 71 | const state = await httpService.get(config.auth.oauth.github.state)
|
---|
| 72 | const clientId = '1024418489231-ml40ukvqcg9ad1h5ejor5dm6ipt6p8fo.apps.googleusercontent.com';
|
---|
| 73 | const redirectUri = encodeURI(`${API_BASE_URL}/oauth/callback/google`);
|
---|
| 74 | const googleAuthUrl = `https://accounts.google.com/o/oauth2/v2/auth?client_id=${encodeURIComponent(clientId)}
|
---|
| 75 | &redirect_uri=${encodeURIComponent(redirectUri)}&state=${encodeURIComponent(state)}&response_type=code&scope=${encodeURIComponent("openid profile email")}`;
|
---|
| 76 | window.location.href = googleAuthUrl
|
---|
[0c6b92a] | 77 | };
|
---|
| 78 |
|
---|
| 79 | return (
|
---|
| 80 | <div className={styles.wrapper}>
|
---|
| 81 | <Logo></Logo>
|
---|
| 82 | <div className={styles.illustration}>
|
---|
| 83 | <img src={illustration} alt="illustration"/>
|
---|
| 84 | </div>
|
---|
| 85 | <div className={styles.form}>
|
---|
| 86 | <div className={styles.heading}>LOGIN</div>
|
---|
| 87 | <form onSubmit={login}>
|
---|
| 88 | <div>
|
---|
| 89 | <label htmlFor="username">Username</label>
|
---|
| 90 | <input
|
---|
| 91 | type="text"
|
---|
| 92 | id="name"
|
---|
| 93 | placeholder="Enter your username"
|
---|
| 94 | onChange={(e) => setFormUsername(e.target.value)}
|
---|
| 95 | value={formUsername}
|
---|
| 96 | required
|
---|
| 97 | />
|
---|
| 98 | </div>
|
---|
| 99 | <div>
|
---|
| 100 | <label htmlFor="password">Password</label>
|
---|
| 101 | <input
|
---|
| 102 | type="password"
|
---|
| 103 | id="password"
|
---|
| 104 | placeholder="Enter your password"
|
---|
| 105 | onChange={(e) => setPassword(e.target.value)}
|
---|
| 106 | value={password}
|
---|
| 107 | required
|
---|
| 108 | />
|
---|
| 109 | </div>
|
---|
| 110 | {error && <p className={styles.error}>{error}</p>}
|
---|
| 111 | <button type="submit">Submit</button>
|
---|
| 112 | </form>
|
---|
[79a0317] | 113 | <div className={styles.or}>OR</div>
|
---|
| 114 | <div className={styles.socialButtons}>
|
---|
| 115 | <button className={styles.socialButton} onClick={continueWithGoogle}>
|
---|
| 116 | <img src={google_icon} alt="Facebook Icon" className={styles.socialIcon}/>
|
---|
| 117 | Sign In With Google
|
---|
| 118 | </button>
|
---|
| 119 | <button className={styles.socialButton} onClick={continueWithGitHub}>
|
---|
| 120 | <img src={github_icon} alt="GitHub Icon" className={styles.socialIcon}/>
|
---|
| 121 | Sign In With GitHub
|
---|
| 122 | </button>
|
---|
| 123 | </div>
|
---|
[0c6b92a] | 124 | <p>
|
---|
| 125 | Don't have an account? <Link to="/Signup"> Sign Up </Link>
|
---|
| 126 | </p>
|
---|
| 127 | </div>
|
---|
| 128 | </div>
|
---|
| 129 | );
|
---|
[d565449] | 130 | };
|
---|
| 131 |
|
---|
[79a0317] | 132 | export default LoginPage; |
---|