0

I am trying to create custom errors for better reporting on my API. I am using a custom class called ValidationError. I create a new object of this class and throw it in try block. Thus, the object now comes into the catch class.

try{
   throw new ValidationError('Balance is insufficient')
}catch(err){
   console.log(err instanceof ValidationError) // returns true
   next(err)
}

So far everything is working fine. next(err) sends the control to this function in app.js

app.use((err , req , res , next)=>{
    console.log(err , err instanceof ValidationError)
    if(err instanceof ValidationError) return res.status(400).json({err : err.message})
    res.status(500).json({err : "Something went wrong. Internal error"})
})

Here this is the result of the console.log :

ValidationError [SequelizeValidationError]: Balance is insufficient
    at C:\Users\ganes\Documents\Software\DFinSerT\Tradilearn\backend\core\Routes\transactions.js:51:18
    at processTicksAndRejections (node:internal/process/task_queues:96:5) {
  errors: []
} false

As you can see, err has the same message so, I assume, it is the same object, but now it is no more an instance of ValidationError.

However, if I reject() an object of Validation error from a custom Promise, The control is not reaching the catch block of the route where the promise was called from. Instead it is directly going to the app.use error handler and this is the output.

ValidationError: Stock does not exists
    at C:\Users\ganes\Documents\Software\DFinSerT\Tradilearn\backend\core\Utils\Validators\stocks.js:11:29
    at processTicksAndRejections (node:internal/process/task_queues:96:5) true

This is the class definition

module.exports = class ValidationError extends Error {
    constructor(message) {
      super(message);
      this.name = this.constructor.name;

      Object.setPrototypeOf(this, ValidationError.prototype);
    }
  }

As you can see, when the validation error is created from a Promise, it does not lose the instance. But when called from catch block using next() it loses the instance. Can someone please explain this behaviour? Thanks.

  • Why are you doing `Object.setPrototypeOf(this, ValidationError.prototype);`? That will be done automatically for you. – T.J. Crowder Oct 01 '22 at 12:58
  • 1
    I assume `SequelizeValidationError` is your class too? What is its definition? It looks like you're using that, not `ValidationError`. – T.J. Crowder Oct 01 '22 at 12:59
  • @T.J.Crowder was trying to debug and came across this https://stackoverflow.com/questions/31626231/custom-error-class-in-typescript. Thus, I just tried it – Ganesh Dagadi Oct 01 '22 at 13:00
  • 1
    Ah. Yes. VScode auto imported the wrong class – Ganesh Dagadi Oct 01 '22 at 13:01
  • 1
    (Re setting the prototype: That question is showing a change **TypeScript** made. You don't want to do that.) The auto-import thing is one of the several reasons not to use default exports. :-) Glad that solved it! – T.J. Crowder Oct 01 '22 at 13:04

0 Answers0