Skip to main content

The super keyword

super gives access to the parent class from inside a child class. As a call, super(...), it runs the parent constructor and creates this; as an object, super.x, it reads members of the parent prototype or of the parent function itself.

Theory

TL;DR

  • super(name) in a constructor calls the parent constructor and initialises this.
  • Before super() runs, touching this throws a ReferenceError.
  • In instance methods super points at Parent.prototype, so super.method() equals Parent.prototype.method.call(this).
  • In static methods super points at Parent itself, that is, at its statics.
  • super() is allowed only inside a class with extends, otherwise it is a SyntaxError.
  • Arrow functions have no super of their own and take it from the surrounding class context.

Quick example

javascript
class Animal { constructor(name) { this.name = name; } } class Dog extends Animal { constructor(name, breed) { super(name); // calls Animal.constructor(name) this.breed = breed; } } const dog = new Dog("Rex", "shepherd"); console.log(dog.name); // "Rex" console.log(dog.breed); // "shepherd"

super() in a constructor: calling the parent

What happens under the hood when one class inherits another:

  1. Before super() is called, the object this does not exist yet.
  2. The call super(name) runs the parent constructor (Animal) and creates this, which can be used from then on.
  3. Only after that may you assign fields on this.

If you try to use this before super(), the engine throws:

javascript
class Dog extends Animal { constructor(name) { this.name = name; // ReferenceError super(name); } }

ReferenceError: Must call super constructor before accessing 'this'

The reason is simple: it is super() that initialises the instance context. Without it this has not been created yet.

super outside a constructor: parent methods

super works not only in the constructor but in any class method, to call the parent implementation.

javascript
class Animal { speak() { console.log("The animal makes a sound"); } } class Dog extends Animal { speak() { super.speak(); // calls the parent method console.log("The dog barks"); } } new Dog().speak(); // "The animal makes a sound" // "The dog barks"

It is equally handy for extending the result of a parent method instead of duplicating its code:

javascript
class Animal { constructor(name) { this.name = name; } info() { return `Name: ${this.name}`; } } class Dog extends Animal { constructor(name, breed) { super(name); // calls Animal.constructor() this.breed = breed; } info() { return `${super.info()}, breed: ${this.breed}`; } } const dog = new Dog("Rex", "Beagle"); console.log(dog.info()); // Name: Rex, breed: Beagle

super in static methods

If a class has static methods, super inside them reaches the parent statics:

javascript
class Parent { static sayHi() { console.log("Hello from the parent"); } } class Child extends Parent { static sayHi() { super.sayHi(); // calls Parent.sayHi() console.log("Hello from the child"); } } Child.sayHi(); // Hello from the parent // Hello from the child

What super actually points at

Under the hood super is a reference to the parent object, and that object differs depending on where you write super:

  • in instance methods super points at Parent.prototype;
  • in static methods super points at Parent itself.

That is why the call:

javascript
super.method()

is equivalent to:

javascript
Parent.prototype.method.call(this)

One important detail: this stays the current instance, so the parent method sees the child data.

super and arrow functions

Arrow functions have no super of their own and take it from the outer context, so super works inside a class arrow field:

javascript
class A { hello() { console.log("Hello from A"); } } class B extends A { hello = () => { super.hello(); // works: super is taken from the class body }; } new B().hello(); // "Hello from A"

Just remember that arrow methods are created on the instance rather than on the prototype, so every object gets its own copy of the function.

Summary:

Where it is usedWhat it does
In a constructorCalls the parent constructor and creates this
In a methodCalls the parent method (super.method())
In a static methodReaches the parent static methods
Without extendsAn error
Before super() is calledthis is unavailable, an error

Common mistakes

  • Calling super() in a class without extends: that is a SyntaxError, because there is no parent at all.
javascript
class A { constructor() { super(); // SyntaxError } }
  • Assigning fields on this before super(). The order is always super(...) first, then this.x = ....
  • Forgetting super() in a child constructor: the constructor fails as soon as it touches this.
  • Expecting super.method() to call the method found through this.__proto__. It does not: super is bound to the class where the method is written, not to the type of the current object.
  • Writing super.constructor() instead of super(). They are different things: only super() creates the instance.

Short Answer

Interview ready
Premium

A concise answer to help you respond confidently on this topic during an interview.