'How does custom made asynchronous wrapper work?
I was following a code along video in Node.JS and creating the backend of a CRUD application. I was able to understand the logic for all the controllers for the routes. However in order to make the code more clean and avoid writing try and catch for each controller, the author started using his own custom asynchronous wrapper for handling error. I am unable to understand the flow of control and how the wrapper and error handling is working. Any help would be really appreciated as I am new to Node.js and JavaScript.
This is the asynchronous wrapper.
const asyncWrapper = (fn) => {
return async (req, res, next) => {
try {
await fn(req, res, next)
} catch (error) {
next(error)
}
}
}
module.exports = asyncWrapper
This is the controller file: -
const Task = require('../models/Task')
const asyncWrapper = require('../middleware/async')
const { createCustomError } = require('../errors/custom-error')
const getAllTasks = asyncWrapper(async (req, res) => {
const tasks = await Task.find({})
res.status(200).json({ tasks })
})
const createTask = asyncWrapper(async (req, res) => {
const task = await Task.create(req.body)
res.status(201).json({ task })
})
const getTask = asyncWrapper(async (req, res, next) => {
const { id: taskID } = req.params
const task = await Task.findOne({ _id: taskID })
if (!task) {
return next(createCustomError(`No task with id : ${taskID}`, 404))
}
res.status(200).json({ task })
})
const deleteTask = asyncWrapper(async (req, res, next) => {
const { id: taskID } = req.params
const task = await Task.findOneAndDelete({ _id: taskID })
if (!task) {
return next(createCustomError(`No task with id : ${taskID}`, 404))
}
res.status(200).json({ task })
})
const updateTask = asyncWrapper(async (req, res, next) => {
const { id: taskID } = req.params
const task = await Task.findOneAndUpdate({ _id: taskID }, req.body, {
new: true,
runValidators: true,
})
if (!task) {
return next(createCustomError(`No task with id : ${taskID}`, 404))
}
res.status(200).json({ task })
})
module.exports = {
getAllTasks,
createTask,
getTask,
updateTask,
deleteTask,
}
And this is the error handler :-
const { CustomAPIError } = require('../errors/custom-error')
const errorHandlerMiddleware = (err, req, res, next) => {
if (err instanceof CustomAPIError) {
return res.status(err.statusCode).json({ msg: err.message })
}
return res.status(500).json({ msg: 'Something went wrong, please try again' })
}
module.exports = errorHandlerMiddleware
And this is the custom error class :-
class CustomAPIError extends Error {
constructor(message, statusCode) {
super(message)
this.statusCode = statusCode
}
}
const createCustomError = (msg, statusCode) => {
return new CustomAPIError(msg, statusCode)
}
module.exports = { createCustomError, CustomAPIError }
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|
