Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 30 additions & 0 deletions backend/middleware/errorHandler.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
export const asyncHandler = (handler) => (req, res, next) => {
Promise.resolve(handler(req, res, next)).catch(next)
}

export const notFoundHandler = (req, res, next) => {
if (res.headersSent) return next()

res.status(404).json({
message: `Route not found: ${req.method} ${req.originalUrl}`,
})
}

export const globalErrorHandler = (err, req, res, next) => {
if (res.headersSent) return next(err)

const statusCode = err.statusCode || err.status || 500
const isServerError = statusCode >= 500

if (isServerError) {
console.error("Unhandled API error:", err)
}

res.status(statusCode).json({
message: isServerError ? "Internal server error." : err.message,
...(process.env.NODE_ENV === "development" && {
error: err.message,
stack: err.stack,
}),
})
}
31 changes: 22 additions & 9 deletions backend/routes/message.routes.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import express from "express"
import { protectRoute } from "../middleware/auth.js"
import { asyncHandler } from "../middleware/errorHandler.js"
import {
getMessages,
getMediaMessages,
Expand Down Expand Up @@ -37,7 +38,7 @@ const messageRouter = express.Router()
* 500:
* description: Internal server error
*/
messageRouter.get("/", protectRoute, getUserForSidebar)
messageRouter.get("/", protectRoute, asyncHandler(getUserForSidebar))

/**
* @swagger
Expand All @@ -62,7 +63,7 @@ messageRouter.get("/", protectRoute, getUserForSidebar)
* 500:
* description: Internal server error
*/
messageRouter.get("/media/:userId", protectRoute, getMediaMessages)
messageRouter.get("/media/:userId", protectRoute, asyncHandler(getMediaMessages))

/**
* @swagger
Expand All @@ -80,7 +81,7 @@ messageRouter.get("/media/:userId", protectRoute, getMediaMessages)
* 500:
* description: Internal server error
*/
messageRouter.get("/sync", protectRoute, syncMessages)
messageRouter.get("/sync", protectRoute, asyncHandler(syncMessages))

/**
* @swagger
Expand All @@ -105,7 +106,7 @@ messageRouter.get("/sync", protectRoute, syncMessages)
* 500:
* description: Internal server error
*/
messageRouter.get("/:userId", protectRoute, getMessages)
messageRouter.get("/:userId", protectRoute, asyncHandler(getMessages))

/**
* @swagger
Expand All @@ -132,8 +133,16 @@ messageRouter.get("/:userId", protectRoute, getMessages)
* 500:
* description: Internal server error
*/
messageRouter.put("/mark-as-seen/:messageId", protectRoute, markMessagesAsSeen)
messageRouter.put("/mark-conversation-seen/:senderId", protectRoute, markConversationSeen)
messageRouter.put(
"/mark-as-seen/:messageId",
protectRoute,
asyncHandler(markMessagesAsSeen),
)
messageRouter.put(
"/mark-conversation-seen/:senderId",
protectRoute,
asyncHandler(markConversationSeen),
)

/**
* @swagger
Expand Down Expand Up @@ -171,8 +180,12 @@ messageRouter.put("/mark-conversation-seen/:senderId", protectRoute, markConvers
* 500:
* description: Internal server error
*/
messageRouter.post("/send/:receiverId", protectRoute, sendMessage)
messageRouter.put("/edit/:messageId", protectRoute, editMessage)
messageRouter.delete("/delete/:messageId", protectRoute, deleteMessage)
messageRouter.post("/send/:receiverId", protectRoute, asyncHandler(sendMessage))
messageRouter.put("/edit/:messageId", protectRoute, asyncHandler(editMessage))
messageRouter.delete(
"/delete/:messageId",
protectRoute,
asyncHandler(deleteMessage),
)

export default messageRouter
27 changes: 16 additions & 11 deletions backend/routes/user.routes.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import {
loginGuest,
} from "../controllers/user.controller.js"
import { protectRoute } from "../middleware/auth.js"
import { asyncHandler } from "../middleware/errorHandler.js"
import { validateBody } from "../middleware/validate.middleware.js"
import {
signupSchema,
Expand Down Expand Up @@ -79,7 +80,7 @@ const userRouter = express.Router()
* 500:
* description: Internal server error
*/
userRouter.post("/signup", validateBody(signupSchema), signup)
userRouter.post("/signup", validateBody(signupSchema), asyncHandler(signup))

/**
* @swagger
Expand Down Expand Up @@ -117,7 +118,7 @@ userRouter.post("/signup", validateBody(signupSchema), signup)
* 500:
* description: Internal server error
*/
userRouter.post("/login", validateBody(loginSchema), login)
userRouter.post("/login", validateBody(loginSchema), asyncHandler(login))

/**
* @swagger
Expand All @@ -135,10 +136,14 @@ userRouter.post("/login", validateBody(loginSchema), login)
* 500:
* description: Internal server error
*/
userRouter.post("/refresh", refresh)
userRouter.post("/logout", logout)
userRouter.post("/send-otp", validateBody(sendOTPSchema), sendOTP)
userRouter.post("/verify-otp", validateBody(verifyOTPSchema), verifyOTP)
userRouter.post("/refresh", asyncHandler(refresh))
userRouter.post("/logout", asyncHandler(logout))
userRouter.post("/send-otp", validateBody(sendOTPSchema), asyncHandler(sendOTP))
userRouter.post(
"/verify-otp",
validateBody(verifyOTPSchema),
asyncHandler(verifyOTP),
)
/**
* @swagger
* /api/v1/auth/guest-login:
Expand Down Expand Up @@ -169,18 +174,18 @@ userRouter.post("/verify-otp", validateBody(verifyOTPSchema), verifyOTP)
* 500:
* description: Internal server error
*/
userRouter.post("/guest-login", loginGuest)
userRouter.post("/guest-login", asyncHandler(loginGuest))
userRouter.post(
"/forgot-password",
validateBody(forgotPasswordSchema),
forgotPassword,
asyncHandler(forgotPassword),
)
userRouter.post(
"/reset-password",
validateBody(resetPasswordSchema),
resetPassword,
asyncHandler(resetPassword),
)
userRouter.get("/check-auth", protectRoute, checkAuth)
userRouter.get("/check-auth", protectRoute, asyncHandler(checkAuth))

/**
* @swagger
Expand Down Expand Up @@ -218,7 +223,7 @@ userRouter.put(
"/update-profile",
protectRoute,
validateBody(updateProfileSchema),
updateProfile,
asyncHandler(updateProfile),
)

export default userRouter
6 changes: 5 additions & 1 deletion backend/server.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import ChallengeRoom from "./models/ChallengeRoom.js"
import { Server } from "socket.io"
import { isVercel, parsePort, getPlatform } from "./lib/runtime.js"
import { registerTypingHandlers } from "./typingHandler.js"
import { globalErrorHandler, notFoundHandler } from "./middleware/errorHandler.js"

const app = express()
const server = http.createServer(app)
Expand Down Expand Up @@ -357,10 +358,13 @@ app.use("/api/v1/messages", standardLimiter, messageRouter)
app.use("/api/v1/problems", standardLimiter, problemRouter)
app.use("/api/v1/challenges", standardLimiter, challengeRouter)

app.use("/", (req, res) => {
app.get("/", (req, res) => {
res.send("NPMChat API is running")
})

app.use(notFoundHandler)
app.use(globalErrorHandler)

// 5. Database Connection
if (process.env.NODE_ENV !== "test") {
connectDB()
Expand Down