Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to Throw custom Errors?

I am trying to use passport-jwt strategy for authentication.

Here is my code :-

router.post('/register', async (req, res) => {
    const { username, email } = req.body;
    try {
        const user = await User.findOne({ username });
        if (user) {
            throw new Error('User with same username already exists !!');
        }
        const newUser = new User({
            username,
            email
        })
        const salt = await bcrypt.genSalt(10);
        newUser.password = await bcrypt.hash(req.body.password, salt);
        const savedUser = await newUser.save();
        res.json({
            status: 200,
            'Content-Type': 'Application/Json',
            'message': `You have successfully regirstered yourself, ${savedUser.username}!`
        })
    } catch (err) {
        err.statusCode = 500;
        console.log(err.message);
        res.header({
            status: '200',
            'Content-Type': 'Application/Json',
        });
        res.json(err);
    }
});

Now this route is working just fine, it's doing all the things till now. The only problem is, When i find an existing user, I want to throw a new error with a custom message. Javascript has this Error class which I can use to throw these errors.

The problem occurs when it catches error. When I console.log(err.message), I can see my custom message perfectly. But the err object that I am returning in response via res.json(err) does not have any message but only statusCode.

I want to know why this is happening and what's the solution for this ? Right now, I am doing this by doing something like this :-

res.json({
    statusCode: 500,
    message : err.message
});

But I would like to return the err object with both statusCode and message fields populated.

like image 537
VIVEK JAIN Avatar asked May 19 '26 03:05

VIVEK JAIN


2 Answers

You can create your own Error class which can take more than one parameter in the constructor. This class has to extend base Error JavaScript class. For example:

class MyCustomError extends Error {
  constructor(msg, statusCode) {
    super(msg);
    this.statusCode = statusCode;
    this.name = MyCustomError.name;
  }
}

function throwCustomError() {
  throw new MyCustomError('Some custom message', 404);
}

try {
  throwCustomError();
} catch (error) {
  console.log(error.message);
  console.log(error.statusCode);
  console.dir(error);
}

Remember that you have to call super on the beginning of the constructor if you are extending another class

like image 183
Krzysztof Kaczyński Avatar answered May 21 '26 17:05

Krzysztof Kaczyński


You are passing the error object to the json method of the response object. But this only takes JSON parseable string as a parameter. What you can do is use -

res.json(JSON.stringify(err))

and at the place where you are using this response, you need to parse this string as JSON and then convert it into an Error object. You can use the following syntax assuming your front-end also uses javascript

err = new Error(JSON.parse(response.data))
like image 26
Aryan Gupta Avatar answered May 21 '26 16:05

Aryan Gupta