๐ ๊ณต๋ถํ๋ ์ง์ง์ํ์นด๋ ์ฒ์์ด์ง?
[E-Commerce App with REST API] (4) login ์ธ์ฆ by jwt & ์ ์ ์ ์ ๋ณด post, get, delete, put ๋ณธ๋ฌธ
[E-Commerce App with REST API] (4) login ์ธ์ฆ by jwt & ์ ์ ์ ์ ๋ณด post, get, delete, put
์ง์ง์ํ์นด 2023. 3. 22. 01:36<๋ณธ ๋ธ๋ก๊ทธ๋ Developers Corner ์ ์ ํ๋ธ๋ฅผ ์ฐธ๊ณ ํด์ ๊ณต๋ถํ๋ฉฐ ์์ฑํ์์ต๋๋ค :-)>
=> Node.js E-Commerce App with REST API: Let's Build a Real-Life Example!
๐ท login ์ ์ ๋ณด๊ฐ ๋ง๋์ง ํ์ธํ๊ธฐ
๊ธฐ์กด ๋น๋ฐ๋ฒํธ์ ์ ๋ ฅํ ๋น๋ฐ๋ฒํธ๊ฐ ๋์ผํ์ง ํ์ธํ๊ธฐ
๐ท jwt (json webtoken)
Header : ์๊ณ ๋ฆฌ์ฆ๊ณผ ํ์
Payload : ๋ฐ์ดํฐ
SIGNATURE : ํ ํฐ์ ์ธ์ฝ๋ฉํ๊ฑฐ๋ ์ ํจ์ฑ ๊ฒ์ฆ์ ํ ๋, ์ฌ์ฉํ๋ ๊ณ ์ ํ ์ฝ๋
=> Header ์ Payload๋ฅผ ํฉ์น ๋ฌธ์์ด์ BASE64๋ก ์ธ์ฝ๋ฉ
=> ์ธ์ฝ๋ฉํ ๊ฐ์ Secret Key๋ฅผ ์ด์ฉํด ํค๋์์ ์ ์ํ ์๊ณ ๋ฆฌ์ฆ์ผ๋ก ํด์ฑ
=> ์ด ๊ฐ์ ๋ค์ BASE64๋ก ์ธ์ฝ๋ฉํ์ฌ ์์ฑ
์ด ์ธ ๋ถ๋ถ์ ํฉ์ณ์ ์ํธํ๋ฅผ ํ ๊ฒ์ด JWT
npm i jsonwebtoken
๐ท role์ผ๋ก ์ฌ์ฉ์ ์ ์ ์ ์ ๋ณด ๊ตฌ๋ถํ๊ธฐ
๐ท login ์ token ๋ฐ๊ธํ๊ธฐ
๐ท ๋ชจ๋ users ์ ๋ณด ๋ณด๊ธฐ
๐ท 1๋ช ์ users ์ ๋ณด ๋ณด๊ธฐ
id๋ก ๋ฐ์์ ์ ์ ์ ๋ณด ๊ฐ๊ณ ์ด
๐ท id๋ก ์ ์ ์ ์ ๋ณด ์ญ์ ํ๊ธฐ
findByIdAndDelete ์ฌ์ฉํจ
๐ท id๋ก ์ ์ ์ ์ ๋ณด ์ ๋ฐ์ดํธ ํ๊ธฐ
findByIdAndUpdate ์ฌ์ฉํจ
๐ท ์ฝ๋
โ controllers/userCtrl.js
const User = require("../models/User");
const bcrypt = require("bcrypt");
const asyncHandler = require("express-async-handler");
const { generateToken } = require("../config/jwtToken");
const createUser = asyncHandler(async (req, res) => {
const { firstname, lastname, email, mobile, password } = req.body;
const findUser = await User.findOne({ email: email });
// email์ด db์ ์๋ค๋ฉด
if (!findUser) {
// Create a new User
// 1) ์ฐ์ ๋น๋ฐ๋ฒํธ ํด์ฌํ(์ํธํ)
const hashedPassword = await bcrypt.hash(password, 10);
// 2) ์ User ์ ๋ณด ๋ง๋ค๊ธฐ
const newUser = await User.create({
firstname, lastname, email, mobile, password: hashedPassword
});
res.json(newUser);
} else {
// User already exists
throw new Error("User already exists");
}
});
const loginCheck = asyncHandler(async (req, res) => {
const { email, password } = req.body;
// check if user exists or not
const findUser = await User.findOne({ email: email });
// user ๊ฐ ์๋ค๋ฉด done
if (!findUser) {
throw new Error("That email is not registered!");
}
// Match password (๊ธฐ์กด ๋น๋ฐ๋ฒํธ์ ์
๋ ฅํ ๋น๋ฐ๋ฒํธ ์ฒดํฌ)
bcrypt.compare(password, findUser.password, (err, isMatch) => {
if (err) throw err;
if (isMatch) {
res.json({
_id: findUser?._id,
firstname: findUser?.firstname,
lastname: findUser?.lastname,
email: findUser?.email,
mobile: findUser?.mobile,
token: generateToken(findUser?._id)
});
} else {
throw new Error("Email or Password is incorrect!");
}
});
})
// Update a user
const updateUser = asyncHandler(async (req, res) => {
const { id } = req.params;
try {
const updateUser = await User.findByIdAndUpdate(id,
{
firstname: req?.body?.firstname,
lastname: req?.body?.lastname,
email: req?.body?.email,
mobile: req?.body?.mobile,
}, {
new : true,
}
);
res.json(updateUser);
} catch (error) {
throw new Error(error);
}
});
// get all users
const getAllUsers = asyncHandler(async (req, res) => {
try {
const getUser = await User.find();
res.json({ getUser });
} catch (error) {
throw new Error(error);
}
});
// get a single users
const getAUsers = asyncHandler(async (req, res) => {
const { id } = req.params;
try {
const getUser = await User.findById(id);
res.json({ getUser });
} catch (error) {
throw new Error(error);
}
});
// delete a user
const deleteAUser = asyncHandler(async (req, res) => {
const { id } = req.params;
try {
const deleteAUser = await User.findByIdAndDelete(id);
res.json({ deleteAUser });
} catch (error) {
throw new Error(error);
}
});
module.exports = {
createUser,
loginCheck,
getAllUsers,
getAUsers,
deleteAUser,
updateUser
};
โ routes/authRoute.js
const express = require("express");
const router = express.Router();
const {createUser, loginCheck, getAllUsers, getAUsers, deleteAUser, updateUser} = require("../controllers/userCtrl");
router.post("/register", createUser);
router.post("/login", loginCheck);
router.get("/all-users", getAllUsers);
router.get("/:id", getAUsers);
router.delete("/:id", deleteAUser);
router.put("/:id", updateUser);
module.exports = router;
โ config/jwtToken.js
const jwt = require("jsonwebtoken");
const generateToken = (id) => {
return jwt.sign({id}, process.env.SECRET, {expiresIn : "3d"});
};
module.exports = {
generateToken
};
โ models/User.js
const mongoose = require("mongoose");
const UserSchema = new mongoose.Schema({
firstname: {
type: String,
required: true
},
lastname: {
type: String,
required: true
},
email: {
type: String,
required: true,
unique: true
},
mobile: {
type: String,
required: true,
unique: true
},
password: {
type: String,
required: true,
},
role: {
type: String,
default: "user",
}
}, { collection: 'Commerce' });
const User = mongoose.model("User", UserSchema);
module.exports = User;