From 67b616ae8dda8b115880974dfcb7a73fe0fbe88b Mon Sep 17 00:00:00 2001 From: Roshan Paudel Date: Sat, 10 Aug 2024 10:02:20 +0545 Subject: [PATCH] =?UTF-8?q?=F0=9F=90=9E=20FIX:=20more=20errors?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/controller/auth.controller.ts | 158 +++++++++++++++--------------- src/helpers/tokens.helper.ts | 22 +++-- 2 files changed, 94 insertions(+), 86 deletions(-) diff --git a/src/controller/auth.controller.ts b/src/controller/auth.controller.ts index 0931cab..eed8c29 100644 --- a/src/controller/auth.controller.ts +++ b/src/controller/auth.controller.ts @@ -1,46 +1,46 @@ -import { Request, Response } from 'express' -import { otpSchema, userSchema } from '../schemas/user.schema' +import { Request, Response } from 'express'; +import { otpSchema, userSchema } from '../schemas/user.schema'; import { BadRequestError, UnauthorizedError, ForbiddenError, -} from '../utils/exceptions' -import { OTPRepo, UserRepository } from '../../repositories' -import * as bcrypt from 'bcrypt' -import { OAuth2Client } from 'google-auth-library' -import { getUserData } from '../helpers/oauth.helper' +} from '../utils/exceptions'; +import { OTPRepo, UserRepository } from '../../repositories'; +import * as bcrypt from 'bcrypt'; +import { OAuth2Client } from 'google-auth-library'; +import { getUserData } from '../helpers/oauth.helper'; -import { getAccessToken, getRefreshToken } from '../helpers/tokens.helper' -import { sendOtp } from '../helpers/email.helpers' +import { getAccessToken, getRefreshToken } from '../helpers/tokens.helper'; +import { sendOtp } from '../helpers/email.helpers'; // Register User export const registerUser = async (req: Request, res: Response) => { - const user = req.body - const parsedData = userSchema.safeParse(user) + const user = req.body; + const parsedData = userSchema.safeParse(user); // Validate data if (!parsedData.success) { - const error = parsedData.error.errors.map((e) => e.message) - throw new BadRequestError(error) + const error = parsedData.error.errors.map((e) => e.message); + throw new BadRequestError(error); } const { data: { email, password, name }, - } = parsedData + } = parsedData; // Check existing users - const existingUser = await UserRepository.findOneBy({ email }) + const existingUser = await UserRepository.findOneBy({ email }); if (existingUser) { - throw new BadRequestError('User already exists.') + throw new BadRequestError('User already exists.'); } // Hash the password - const saltRounds = 10 - const salt = await bcrypt.genSalt(saltRounds) - const hash = await bcrypt.hash(password + salt, salt) + const saltRounds = 10; + const salt = await bcrypt.genSalt(saltRounds); + const hash = await bcrypt.hash(password + salt, salt); // Generate token and refreshToken - const refreshToken = getRefreshToken({ email }) + const refreshToken = getRefreshToken({ email }); const result = await UserRepository.save({ name, hash, @@ -48,83 +48,83 @@ export const registerUser = async (req: Request, res: Response) => { email, verified: false, refreshToken, - }) + }); - const newOtp = OTPRepo.create({ user: result, otp: '123456' }) - await OTPRepo.save(newOtp) - await sendOtp({ name, email, otp: 123456 }) + const newOtp = OTPRepo.create({ user: result, otp: '123456' }); + await OTPRepo.save(newOtp); + await sendOtp({ name, email, otp: 123456 }); return res.status(200).json({ message: 'User created successfully !!', - }) -} + }); +}; // Get all userSchema export const getAllUsers = async (_: Request, res: Response) => { - const users = await UserRepository.find() - return res.json(users) -} + const users = await UserRepository.find(); + return res.json(users); +}; // Get all userSchema export const verifyOTP = async (req: Request, res: Response) => { - const body = req.body - const parsedData = otpSchema.safeParse(body) - console.log(body) + const body = req.body; + const parsedData = otpSchema.safeParse(body); + console.log(body); - if (!parsedData.success) throw new BadRequestError('Invalid data.') + if (!parsedData.success) throw new BadRequestError('Invalid data.'); - const { email, otp } = parsedData.data - const user = await UserRepository.findOneBy({ email }) + const { email, otp } = parsedData.data; + const user = await UserRepository.findOneBy({ email }); - if (!user) throw new BadRequestError('User not found.') + if (!user) throw new BadRequestError('User not found.'); - const dbOtp = await OTPRepo.findOneBy({ user }) - if (!dbOtp) throw new BadRequestError('OTP not found.') - if (otp !== dbOtp.otp) throw new BadRequestError('Invalid OTP.') + const dbOtp = await OTPRepo.findOneBy({ user }); + if (!dbOtp) throw new BadRequestError('OTP not found.'); + if (otp !== dbOtp.otp) throw new BadRequestError('Invalid OTP.'); // Delete OTP - await OTPRepo.delete(dbOtp) + await OTPRepo.delete(dbOtp); // VERIFY USER - user.verified = true - await UserRepository.save(user) + user.verified = true; + await UserRepository.save(user); - return res.json({ message: 'OTP verifed.' }) -} + return res.json({ message: 'OTP verifed.' }); +}; // LOGIN USER export const loginUser = async (req: Request, res: Response) => { - const { email, password } = req.body - const user = await UserRepository.findOneBy({ email }) + const { email, password } = req.body; + const user = await UserRepository.findOneBy({ email }); - if (!user) throw new UnauthorizedError('Invalid email or password.') + if (!user) throw new UnauthorizedError('Invalid email or password.'); if (!(await user.validatePassword(password))) - throw new UnauthorizedError('Invalid email or password.') + throw new UnauthorizedError('Invalid email or password.'); - if (!user.verified) throw new ForbiddenError('Please verify OTP first.') + if (!user.verified) throw new ForbiddenError('Please verify OTP first.'); - const payload = { id: user.id, email: user.email, picture: user.picture } - const accessToken = getAccessToken(payload) + const payload = { id: user.id, email: user.email, picture: user.picture }; + const accessToken = getAccessToken(payload); - return res.json({ user, accessToken }) -} + return res.json({ user, accessToken }); +}; // REFRESH TOKEN export const refreshUserToken = async (req: Request, res: Response) => { - const { refreshToken } = req.body - if (!refreshToken) throw new BadRequestError('No refreshtoken provided !!') + const { refreshToken } = req.body; + if (!refreshToken) throw new BadRequestError('No refreshtoken provided !!'); - const user = await UserRepository.findOneBy({ refreshToken }) - if (!user) throw new UnauthorizedError('Invalid credentials !!') + const user = await UserRepository.findOneBy({ refreshToken }); + if (!user) throw new UnauthorizedError('Invalid credentials !!'); - const newAccessToken = getAccessToken({ id: user.id }) + const newAccessToken = getAccessToken({ id: user.id }); return res.json({ user, accessToken: newAccessToken, - }) -} + }); +}; // OAUTH POST export const googleOauthPost = async (req: Request, res: Response) => { @@ -132,37 +132,37 @@ export const googleOauthPost = async (req: Request, res: Response) => { process.env.CLIENT_ID, process.env.CLIENT_SECRET, process.env.REDIRECT_URL, - ) + ); const authorizeUrl = oauthClient.generateAuthUrl({ access_type: 'offline', scope: 'https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email openid ', // prompt: "consent", - }) + }); - return res.json({ url: authorizeUrl }) -} + return res.json({ url: authorizeUrl }); +}; // OAUTH GET export const googleOauthGet = async (req: Request, res: Response) => { - const { code } = req.query + const { code } = req.query; const oauthClient = new OAuth2Client( process.env.CLIENT_ID, process.env.CLIENT_SECRET, process.env.REDIRECT_URL, - ) + ); - const oauthRes = await oauthClient.getToken(code as string) - await oauthClient.setCredentials(oauthRes.tokens) - const user = oauthClient.credentials + const oauthRes = await oauthClient.getToken(code as string); + await oauthClient.setCredentials(oauthRes.tokens); + const user = oauthClient.credentials; // EXTRACT NECESSARY INFO FROM GOOGLE - const { sub, name, picture, email } = await getUserData(user.access_token!) + const { sub, name, picture, email } = await getUserData(user.access_token!); // Find user with that google id and if not user create a user - const existingUser = await UserRepository.findOneBy({ googleId: sub, email }) + const existingUser = await UserRepository.findOneBy({ googleId: sub, email }); // Encrypt data and return if (existingUser) { @@ -170,12 +170,12 @@ export const googleOauthGet = async (req: Request, res: Response) => { id: existingUser.id, name: existingUser.name, picture: existingUser.picture, - }) + }); const refreshToken = getRefreshToken({ id: existingUser.id, name: existingUser.name, picture: existingUser.picture, - }) + }); return res.json({ user: { @@ -186,7 +186,7 @@ export const googleOauthGet = async (req: Request, res: Response) => { }, accessToken, refreshToken, - }) + }); } // Create new user & Encrypt data and return @@ -195,10 +195,10 @@ export const googleOauthGet = async (req: Request, res: Response) => { picture, email, googleId: sub, - }) + }); - const accessToken = getAccessToken(newUser) - const refreshToken = getRefreshToken(newUser) + const accessToken = getAccessToken(newUser); + const refreshToken = getRefreshToken(newUser); - return res.json({ user: newUser, accessToken, refreshToken }) -} + return res.json({ user: newUser, accessToken, refreshToken }); +}; diff --git a/src/helpers/tokens.helper.ts b/src/helpers/tokens.helper.ts index b7f31b5..d3b9679 100644 --- a/src/helpers/tokens.helper.ts +++ b/src/helpers/tokens.helper.ts @@ -1,15 +1,23 @@ import * as jwt from 'jsonwebtoken'; +import { User } from '../entity'; -export const getAccessToken = (payload: Record) => { - return jwt.sign(payload, process.env.JWT_SECRET, { +type Payload = Partial>; + +export const getAccessToken = (payload: Payload) => { + return jwt.sign(payload, process.env.JWT_SECRET || 'secret', { algorithm: 'HS256', expiresIn: '15m', }); }; -export const getRefreshToken = (payload: Record) => { - return jwt.sign(payload, process.env.REFRESH_TOKEN_SECRET, { - algorithm: 'HS256', - expiresIn: '15m', - }); +export const getRefreshToken = (payload: Payload) => { + console.log(payload); + return jwt.sign( + payload, + process.env.REFRESH_TOKEN_SECRET || 'refresh-token-secret', + { + algorithm: 'HS256', + expiresIn: '15m', + }, + ); };