Reputation: 25
I am working on displaying the current user's information, such as their username and email, on the account page of my application. I am using JWT for authentication, but I am consistently encountering issues. How to properly implement this functionality?
user.model.js:
import mongoose from 'mongoose';
const UserSchema = new mongoose.Schema({
username: {
type: String,
required: [true, 'Username is required'],
unique: true,
},
email: {
type: String,
required: [true, 'Email is required'],
unique: true,
},
password : {
type: String,
required: [true, 'Password is required'],
},
role : {
type: String,
enum: ['Admin','User'],
default: 'User'
}
})
const User = mongoose.model('User', UserSchema);
export default User;
user.controller.js:
import User from "../models/user.model.js";
import bcrypt from "bcrypt";
import jwt from "jsonwebtoken";
import dotenv from "dotenv";
dotenv.config();
const SECRET_KEY = process.env.SECRET_KEY;
export const createUser = async (req, res) => {
try {
const { username, email,password} = req.body;
const hashedPassword = await bcrypt.hash(password, 10);
const newUser = new User({ username,email, password: hashedPassword });
await newUser.save();
res.status(201).json({ success: true , message: 'User created successfully' });
}
catch(err){
res.status(500).json({ success: false, message: err.message });
}
}
export const getUsers = async (req, res) => {
try {
const users = await User.find();
res.status(200).json({ success: true, data: users });
}
catch(err){
res.status(500).json({ success: false, message: err.message });
}
}
export const loginUser = async (req, res) => {
try{
const {username,password} = req.body;
const user = await User.findOne({username});
if(!user){
return res.status(404).json({ success: false, message: 'Username or password is incorrect' });
}
const isPasswordValid = await bcrypt.compare(password, user.password);
if(!isPasswordValid){
return res.status(401).json({ success: false, message: 'Username or password is incorrect' });
}
const token = jwt.sign({ userId: user._id}, SECRET_KEY, { expiresIn: '1h' })
res.status(200).json({ success: true, message: 'Login successful' } );
}
catch(err){
res.status(500).json({ success: false, message: err.message });
}
}
export const getUserInfo = async (req, res) => {
try {
const user = await User.findById(req.params.id).select('-password'); // Exclude the password
if (!user) {
return res.status(404).json({ message: 'User not found' });
}
res.status(200).json(user);
} catch (error) {
res.status(500).json({ message: error.message });
}
}
SignUp.jsx:
import React,{useState} from 'react';
import { Box, Center, Input, Button ,Divider } from '@chakra-ui/react';
import { useNavigate } from 'react-router-dom';
import axios from 'axios';
const SignUp = () => {
const [username,setUsername] = useState("");
const [email,setEmail] = useState("");
const [password,setPassword] = useState("");
const navigate = useNavigate();
const handleRegister = async (event) => {
event.preventDefault();
axios.post('http://localhost:5000/api/auth/register',{username,email,password})
.then(()=>{
setUsername("");
setEmail("");
setPassword("");
alert("User registered successfully");
navigate("/login");
}).catch((err) =>{
console.log(err);
})
}
return (
<Box
display="flex"
alignItems="center"
justifyContent="center"
minHeight="100vh"
>
<Box
w="400px"
p="6"
boxShadow="lg"
borderRadius="md"
background="white"
>
<Center>
<h1 style={{fontSize:"25px" , fontWeight: "bold", fontFamily: "sans-serif"}}>Sign Up</h1>
</Center>
<br />
<Divider />
<br />
<form onSubmit={handleRegister}>
<label htmlFor="username">Username</label>
<Input
id="username"
type="text"
placeholder="Enter your username"
mt="2"
mb="4"
value={username}
onChange ={(e) => setUsername(e.target.value)}
/>
<label htmlFor="email">Email</label>
<Input
id="email"
type="email"
placeholder="Enter your email"
mt="2"
mb="4"
value={email}
onChange ={(e) => setEmail(e.target.value)}
/>
<label htmlFor="password">Password</label>
<Input
id="password"
type="password"
placeholder="Enter your password"
mt="2"
mb="4"
value={password}
onChange ={(e) => setPassword(e.target.value)}
/>
<Button type="submit" backgroundColor={'#CBD5E0'} width="full" mt="4" >Sign Up</Button>
</form>
</Box>
</Box>
);
}
export default SignUp;
Login.jsx:
import React,{useState , useEffect} from 'react';
import { Box, Center, Input, Button ,Divider } from '@chakra-ui/react';
import { useNavigate } from 'react-router-dom';
import axios from 'axios';
const Login = () => {
const [user , setUsers] = useState([])
const [username, setUsername] = useState("");
const [password, setPassword] = useState("");
const navigate = useNavigate();
const handleLogin = async (event)=>{
event.preventDefault();
try{
const response = await axios.post('http://localhost:5000/api/auth/login',{username,password});
const token = response.data.token;
console.log(token);
setUsername("");
setPassword("");
// navigate('/');
// window.location.reload();
localStorage.setItem('token',token);
} catch(err){}
}
return (
<Box
display="flex"
alignItems="center"
justifyContent="center"
minHeight="100vh"
>
<Box
w="400px"
p="6"
boxShadow="lg"
borderRadius="md"
background="white"
>
<Center>
<h1 style={{fontSize:"25px" , fontWeight: "bold", fontFamily: "sans-serif"}} >Login</h1>
</Center>
<br />
<Divider />
<br />
<form onSubmit={handleLogin}>
<label htmlFor="email">Username</label>
<Input
id="username"
type="username"
placeholder="Enter your username"
mt="2"
mb="4"
value={username}
onChange ={(e) => setUsername(e.target.value)}
/>
<label htmlFor="password">Password</label>
<Input
id="password"
type="password"
placeholder="Enter your password"
mt="2"
mb="4"
value={password}
onChange ={(e) => setPassword(e.target.value)}
/>
<Button type="submit" backgroundColor={'#CBD5E0'} width="full" mt="4">Login</Button>
</form>
</Box>
</Box>
);
}
export default Login;
Account.jsx
I am unsure what to include after retrieving the username and email. I have tried various approaches, but the token always appears as undefined. I checked the local storage through the browser's developer tools, and it is also showing as undefined. Could someone please assist me in resolving this issue?
import React from 'react'
import { useState, useEffect } from 'react';
import {Center,Box} from '@chakra-ui/react';
const Account = () => {
return (
<Center>
<Box>
username :
email :
</Box>
</Center>
)
}
export default Account;
Upvotes: 0
Views: 33