Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Calling constructor of parent class in static method of child class

I got a problem with calling super inside of the child static method.

const _todos = [];

class Todo {
  constructor(title) {
    this.title = title;
    this.id = Math.round(Math.random() * 100);
    _todos.push({title, id: this.id});

    console.log(`Todo ID: ${this.id}. DONT FORGET IT!`);
  }

  static TodoerVersion = '1.8';

  static removeTodo(id) {
    const todoIndex = _todos.findIndex(t => t.id == id);
    _todos.splice(todoIndex, 1);
  }
}

class TodoV2 extends Todo {
  static addTodo(title) {
    super(title);
  }

  static addDescription(todo, description) {
    todo.description = description;
  }

  static TodoerVersion = '2.0';
};

new TodoV2("play guitar");

Why does it not work?
But if i call super in normal method, it would works just fine.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

>Solution :

super is only callable within the constructor function of a class.

Two answers for you:

  1. The question you actually asked.

  2. What I think you should do instead. 🙂

Answering the question you asked:

JavaScript is very special in this regard: this has meaning in static methods (as long as you call them correctly, e.g. TodoV2.addTodo("title")): it’s the constructor function you called the static method on. And a subclass constructor function inherits from its superclass constructor function (yes, really). So you can access the constructor function for the parent class using Object.getPrototypeOf(this) in the static method:

// This is something unusual that JavaScript actually does support
static addTodo(title) {
    const ctor = Object.getPrototypeOf(this);
    return new ctor(title);
}

To handle the case where the user may have called addTodo in a way that doesn’t set this, you might do something like this to default to TodoV2 if this is undefined:

static addTodo(title) {
    const ctor = Object.getPrototypeOf(this ?? TodoV2);
    return new ctor(title);
}

What I think you should do instead

You shouldn’t be using a static method for this. Instead, define a constructor for TodoV2:

class TodoV2 extends Todo {
    constructor(title, description) {
        super(title);
        this.description = description ?? "";
    }

    static addTodo(title) { // Why no `description`?
        return new this(title); // Or `new TodoV2(title)`
    }
}

You might also look into the Symbol.species pattern if you want subclasses to create instances of superclasses.

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading