DEV Community

Luka Vidaković
Luka Vidaković

Posted on

Custom error types in Node.js

Custom error types in node can provide a clearer picture of a failure. Relying on generic errors often leaves us guessing what had happened down the chain. Custom errors can help us identify certain, well known sets of failures and even subclass them for a more generalized handler functions.

In this series of posts we'll go from constructing a simplest possible custom error(this post) to defining a few, well known HTTP errors and using them inside an Express.js HTTP server framework to craft automatic error responses.

Simplest way to create a custom error type is to just extend an Error's prototype and initialize the original Error through a constructor:

class MyError extends Error {
  constructor(message) {
    super(message)
  }
}
Enter fullscreen mode Exit fullscreen mode

That's it!

The message we pass from the constructor to the "super" call is actually the same parameter you'd pass with the new Error('Something failed!'). Message is just forwarded to the same constructor to set up an error with a message and a stack trace.

There are 2 small things to fix though. If you log out the error created with MyError class:

const error = new MyError('problem')
console.log(error)
Enter fullscreen mode Exit fullscreen mode

You'll notice that error type is logged as "Error":

Error: problem
    at <anonymous>:1:15
Enter fullscreen mode Exit fullscreen mode

To fix this we just need to augment our error object with a "name" property inside constructor:

  constructor(message) {
    super(message)
    this.name = 'MyError'
  }
Enter fullscreen mode Exit fullscreen mode

Now if we try previous example we'll see something like:

MyError: problem
    at <anonymous>:1:15
Enter fullscreen mode Exit fullscreen mode

1/2 fixed. The only thing remaining is that our stack trace might include the mention of our custom error class constructor. We don't want to see an error creation in our stack frames, only the real code that caused the issue. Fix is simple, single additional line in the constructor will take care of that:

  Error.captureStackTrace(this, MyError)
Enter fullscreen mode Exit fullscreen mode

This will omit all of the stack frames invoked by code inside MyError itself.

The final code is:

class MyError extends Error {
  constructor(message) {
    super(message)
    this.name = 'MyError'
    Error.captureStackTrace(this, MyError)
  }
}
Enter fullscreen mode Exit fullscreen mode

In next post we'll go from custom error type to a custom error subtype that will enable us to treat all of our custom error types in a generic way.

Top comments (2)

Collapse
 
renuja99 profile image
Renuja De Costa

Beautifully explained

Collapse
 
_tahir_official profile image
Abu Tahir

Very helpful, thank you!