Extending Error in Javascript with ES6 syntax & Babel Extending Error in Javascript with ES6 syntax & Babel javascript javascript

Extending Error in Javascript with ES6 syntax & Babel


Based on Karel BĂ­lek's answer, I'd make a small change to the constructor:

class ExtendableError extends Error {  constructor(message) {    super(message);    this.name = this.constructor.name;    if (typeof Error.captureStackTrace === 'function') {      Error.captureStackTrace(this, this.constructor);    } else {       this.stack = (new Error(message)).stack;     }  }}    // now I can extendclass MyError extends ExtendableError {}var myerror = new MyError("ll");console.log(myerror.message);console.log(myerror instanceof Error);console.log(myerror.name);console.log(myerror.stack);

This will print MyError in the stack, and not the generic Error.

It will also add the error message to the stack trace - which was missing from Karel's example.

It will also use captureStackTrace if it's available.

With Babel 6, you need transform-builtin-extend (npm) for this to work.


Combining this answer, this answer and this code, I have made this small "helper" class, that seems to work fine.

class ExtendableError extends Error {  constructor(message) {    super();    this.message = message;     this.stack = (new Error()).stack;    this.name = this.constructor.name;  }}    // now I can extendclass MyError extends ExtendableError {  constructor(m) {       super(m);  }}var myerror = new MyError("ll");console.log(myerror.message);console.log(myerror instanceof Error);console.log(myerror.name);console.log(myerror.stack);

Try in REPL


To finally put this to rest. In Babel 6 it is explicit that the developers do not support extending from built in. Although this trick will not help with things like Map, Set, etc. it does work for Error. This is important as one of the core ideas of a language that can throw an exception is to allow custom Errors. This is doubly important as Promises become more useful since they to are designed to reject an Error.

The sad truth is you still need to perform this the old way in ES2015.

Example in Babel REPL

Custom Error pattern

class MyError {  constructor(message) {    this.name = 'MyError';    this.message = message;    this.stack = new Error().stack; // Optional  }}MyError.prototype = Object.create(Error.prototype);

On the other hand there is a plugin for Babel 6 to allow this.

https://www.npmjs.com/package/babel-plugin-transform-builtin-extend

Update: (as of 2016-09-29) After some testing it appears that babel.io does not properly account for all the asserts (extending from a custom extended Error). But in Ember.JS extending Error works as expected: https://ember-twiddle.com/d88555a6f408174df0a4c8e0fd6b27ce