瀏覽代碼

Feature: Refactor logout process to utilize context for userId and token, and enhance error handling

BedirhanOZCAN 1 月之前
父節點
當前提交
fc84638a8f
共有 3 個文件被更改,包括 60 次插入31 次删除
  1. 1 11
      src/actions/auth/logout/index.ts
  2. 15 3
      src/controllers/authController.ts
  3. 44 17
      src/middlewares/authMiddleware.ts

+ 1 - 11
src/actions/auth/logout/index.ts

@@ -1,4 +1,3 @@
-import jwt from "jsonwebtoken";
 import {
     User
 } from "../../../models/User";
@@ -13,16 +12,7 @@ export const logout = async (userId: string, token: string): Promise<LogoutResul
             refreshToken: null
         });
 
-        const decoded = jwt.decode(token) as { exp?: number };
-
-        if (decoded && decoded.exp) {
-            const currentTime = Math.floor(Date.now() / 1000);
-            const timeToExpire = decoded.exp - currentTime;
-
-            if (timeToExpire > 0) {
-                await redis.setex(`bl_${token}`, timeToExpire, "blacklisted");
-            }
-        }
+        await redis.del(`user:${userId}`);
 
         return {
             message: "Logout successful",

+ 15 - 3
src/controllers/authController.ts

@@ -81,12 +81,24 @@ export const login = async (req: Request, res: Response): Promise<void> => {
 
 export const logout = async (req: AuthRequest, res: Response): Promise<void> => {
     try {
-        const userId = req.userId;
-        const token = req.token;
+        const context = req.context;
+
+        if (!context) {
+            res.status(401).json({
+                message: "Unauthorized: Missing context",
+                code: 401
+            });
+            return;
+        }
+
+        const {
+            userId,
+            token
+        } = context;
 
         if (!userId || !token) {
             res.status(401).json({
-                message: "Unauthorized",
+                message: "Unauthorized: Missing user information",
                 code: 401
             });
             return;

+ 44 - 17
src/middlewares/authMiddleware.ts

@@ -6,46 +6,73 @@ import redis from "../config/redis";
 import {
     User
 } from "../models/User";
-
 export interface AuthRequest extends Request {
-    userId?: string;
-    token?: string;
+    context?: {
+        userId: string;
+        token: string;
+    };
 }
 
 export const authMiddleware = async (req: AuthRequest, res: Response, next: NextFunction): Promise<void> => {
     try {
-        const authHeader = req.headers.authorization;
+        const token = req.headers.authorization;
 
-        if (!authHeader || !authHeader.startsWith("Bearer ")) {
+        if (!token) {
             res.status(401).json({
-                message: "Token not found",
-                code: 401
+                message: "token-not-found", code: 401
             });
             return;
         }
 
-        const token = authHeader.split(" ")[1];
+        let decoded: { userId: string };
+        try {
+            decoded = jwt.verify(token, process.env.JWT_SECRET as string) as { userId: string };
+        } catch (err) {
+            res.status(401).json({
+                message: "expired-token", code: 401
+            });
+            return;
+        }
 
-        const isBlacklisted = await redis.get(`bl_${token}`);
+        if (!decoded || !decoded.userId) {
+            res.status(401).json({
+                message: "invalid-token", code: 401
+            });
+            return;
+        }
 
-        if (isBlacklisted) {
+        const cachedToken = await redis.get(`user:${decoded.userId}`);
+        if (!cachedToken) {
             res.status(401).json({
-                message: "Your session has ended, please log in again.",
-                code: 401
+                message: "expired-token", code: 401
             });
             return;
         }
 
-        const decoded = jwt.verify(token, process.env.JWT_SECRET as string) as { userID: string };
+        if (cachedToken !== token) {
+            res.status(401).json({
+                message: "invalid-token", code: 401
+            });
+            return;
+        }
 
-        req.userId = decoded.userID;
-        req.token = token;
+        const user = await User.findById(decoded.userId);
+        if (!user) {
+            res.status(401).json({
+                message: "user-not-found", code: 401
+            });
+            return;
+        }
 
+        req.context = {
+            userId: decoded.userId,
+            token: token
+        };
         next();
+
     } catch (error) {
         res.status(401).json({
-            message: "Invalid or expired tokens",
-            code: 401
+            message: "invalid-token", code: 401
         });
     }
 };