Middleware in Express allows you to customize and enhance the request-response cycle. One powerful application of middleware is to format the response before it is sent back to the client.
We'll explore how to create a middleware function to expose only specific user fields and restrict fields like password, _id etc.
Route
import { Router } from "express";
const router = Router();
router.get("/profile", getUserProfile, UserResponse);
Controller
We are fetching user details based on request POST param userId
.
user
returns Mongoose User but we don't want to expose all fields in our response. Therefore, we can assign the response json to res.locals
so that it can be passed on to the middleware.
Ref:
/* User profile details */
export const getUserProfile = async (
req: Request,
res: Response,
next: NextFunction
) => {
try {
const { userId } = req;
if (!userId ) {
return res.status(400).json({
status: 0,
data: null,
error: "User not found",
});
}
const user = User.findById(userId);
// Store data here, which can be accessed in middleware
res.locals.apiResponse = {
status: 1,
data: user,
};
next(); // this is important so that it's forwarded to UserResponse middleware
} catch (error) {
res.status(500).json({ status: API_STATUS.ERROR, error });
}
};
Creating the middleware
import { NextFunction, Request, Response } from "express";
export const UserResponse = (
req: Request,
res: Response,
Next: NextFunction
) => {
try {
if (res.locals?.apiResponse) {
if (
res.locals.apiResponse?.status == 1 &&
typeof res.locals.apiResponse?.data === "object" &&
res.locals.apiResponse?.data.constructor.modelName === "User"
) {
const tempUser = res.locals.apiResponse?.data.toObject();
/* Delete all private fields so that only necessary fields are exposed */
delete tempUser._id;
delete tempUser.createdAt;
delete tempUser.updatedAt;
delete tempUser.password;
delete tempUser?.__v;
return res.status(200).json({
status: res.locals.apiResponse?.status,
data: tempUser,
});
}
}
return res.status(200).json(res.locals);
} catch (error) {
res.status(500).json({ status: 0, error });
}
};
Top comments (0)