2

So I've been googling this for a few hours now and I can't really decide whether it's possible or not. I don't understand JS inheritance well enough to find a solution. I'm working in TypeScript, but I think this is a JavaScript issue. Platform is Node.js.

My setup is the following:

class Message {
    static fromBytes(bytes) {
        someChecks();
        return new Message(processedBytes);
    }
    constructor(someParameters) {
        someOtherChecks();
    }
}

class SpecificMessage extends Message {
    constructor(parameters) {
        someSpecificChecks(parameters);
    }
}

The background is that I get some bytes network traffic and have to check consistency before decoding it. The classes are also used to prepare new outgoing bytes (there's a toBytes method), which is why checksum consistency is checked in fromBytes and logical consistency is checked in the constructor.

What I'd like to have is an inheritable factory method that will return the respective object type. Calling SpecificMessage.fromBytes will return a Message object since it's explicitly named. I'd like to replace that object creation with something that "knows" whether I'm calling from Message or SpecificMessage. My best guess in that direction is something along the lines of Object.create(this.prototype, {someInitLiteral}), but I think this doesn't call the constructor?

Another thing that came up was Object.call(this, parameters), but I don't think that's correct either. Is there a way to instantiate the current class from the "generic" static method?

Worst case I was thinking about just calling super.fromBytes and create a new SpecificMessage from the contained data. That would construct two objects but go through all the checks.

Thank your for your help.

Bergi
  • 630,263
  • 148
  • 957
  • 1,375
Randelung
  • 356
  • 4
  • 10

1 Answers1

2

As you seem to have realised, the this keyword would refer to the constructor (= the (sub)class) inside the static method1. So you can just call that with new:

class Message {
    static fromBytes(bytes) {
        someChecks();
        return new this(processedBytes);
//             ^^^^^^^^
    }
    constructor(someParameters) {
        // …
    }
}

1: As long as it is called as a method on the respective class. You can no longer easily pass it around as a callback.

Bergi
  • 630,263
  • 148
  • 957
  • 1,375