1

In a static method in a base class, is it possible to name the currently class's instance type?

Put another way, can you make this code type check:

class Base {
  static addInitializer(i: (v: any /* What type would go here? */) => void) {
    // implementation is irrelevent
  }
}

class Dog extends Base {
  bark() {}
}

class Fish extends Base {
  swim() {}
}

Dog.addInitializer((dog) => {
  dog.bark();
  // @ts-expect-error
  dog.swim();
});

Fish.addInitializer((fish) => {
  fish.swim();
  // @ts-expect-error
  fish.bark();
});

Note the use of // @ts-expect-error before lines that should be a type error. They're highlighted as 'unused' because v has type any rather than the type I'm trying to name here.

TypeScript playground link

1 Answer 1

1

By making the static method generic and constrained by the this param of the static method you can make the type of the class that you call the static method on available. From there, just use the InstanceType operator, like so:

class Base {
  static addInitializer<T extends new (...args: any) => Base>(this: T, init: (e: InstanceType<T>) => void) {
    // implementation is irrelevent
  }
}

class Dog extends Base {
  bark() {}
}

class Fish extends Base {
  swim() {}
}

Dog.addInitializer((dog) => {
  dog.bark();
  // @ts-expect-error
  dog.swim();
});

Fish.addInitializer((fish) => {
  fish.swim();
  // @ts-expect-error
  fish.bark();
});
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.